Comparar commits

...

143 Commits

Autor SHA1 Mensagem Data
etimberg c074d3b7d4 Update built files 2015-11-30 21:35:09 -05:00
Evert Timberg 6cce958548 Merge pull request #1720 from nnnick/fix/1718
Allow the user to change the time label display formats
2015-11-30 20:50:00 -05:00
etimberg ccb1c68b65 Update docs 2015-11-30 20:47:49 -05:00
etimberg f609452727 Allow the user to change the time label display formats 2015-11-30 20:42:48 -05:00
Evert Timberg b2150b93a2 New built files + some sample file updates 2015-11-29 13:33:24 -05:00
Evert Timberg b9fa20714f Merge pull request #1713 from nnnick/v2.0-beta1-docs
Initial docs to get ready for beta1
2015-11-29 13:13:01 -05:00
Evert Timberg e5ee242dc6 Merge branch 'v2.0-dev' into v2.0-beta1-docs
Conflicts:
	docs/01-Scales.md
2015-11-29 11:32:57 -05:00
Evert Timberg 9dbc5650ed Initial update to line and bar docs 2015-11-29 11:30:39 -05:00
Evert Timberg 0052ceb7a1 Initial update to scale documentation 2015-11-29 10:58:01 -05:00
Evert Timberg e91e6be851 Merge pull request #1696 from nnnick/fix/1688
When tooltip opacity is less than 1e-3, round to 0.
2015-11-29 10:16:25 -05:00
Evert Timberg 349586e14c Merge pull request #1695 from nnnick/fix/consistent-display-parameters
Fix inconsistent display parameters
2015-11-29 10:16:20 -05:00
Evert Timberg c4b30a7b0e Update getting started docs 2015-11-29 10:04:46 -05:00
Evert Timberg f0555af8cc Another build 2015-11-27 17:37:42 -05:00
Evert Timberg e5244b7dba Merge branch 'v2.0-dev' of https://github.com/nnnick/Chart.js into v2.0-dev 2015-11-27 17:37:14 -05:00
Evert Timberg bf2ca8bd0b Push up new built files 2015-11-27 17:35:34 -05:00
Evert Timberg f4bcef13f5 Merge pull request #1704 from Marius2805/v2.0-dev
V2.0 Docs: Fixed wrong example data structure for Pie/Doughnut Chart
2015-11-27 07:25:22 -05:00
Evert Timberg efdc23c567 Merge pull request #1703 from wuchangming/v2.0-dev
V2.0 dev 	Bug in handler event.type='touchend'
2015-11-27 07:24:53 -05:00
Marius Meißner e84d27dde7 Fixed wrong structure of example data 2015-11-27 08:34:32 +01:00
wuchangming 7aa2fd1af3 Bug in handler event.type='touchend'
In Chorme.
while event.type = "touchend” ,  event.touches is a empty TouchList,
event.touches.length === 0
2015-11-27 11:16:54 +08:00
wuchangming 5a1c968105 Merge remote-tracking branch 'nnnick/v2.0-dev' into v2.0-dev 2015-11-27 08:50:55 +08:00
Evert Timberg e87fd9e0cc Merge pull request #1702 from wuchangming/v2.0-dev
no such file
2015-11-26 07:41:23 -05:00
wuchangming dae1e429b8 no such file 2015-11-26 19:35:25 +08:00
Evert Timberg 55670b0cf7 When opacity is less than 1e-3, round to 0. IE11/Edge had problems with very small opacities on the order of 1e-10. 2015-11-25 19:31:26 -05:00
Evert Timberg 5f7507c324 Update docs 2015-11-24 19:21:09 -05:00
Evert Timberg a90aac7b26 Change scale show properties to display and update tests 2015-11-24 19:18:15 -05:00
Evert Timberg cf1f772157 Merge pull request #1693 from wcatron/basic-documentation
Add descriptions for options in documentation.
2015-11-24 18:22:33 -05:00
wcatron 8e9fef27c2 Add more explanation of bar and category percentage. 2015-11-24 14:25:15 -05:00
wcatron 75fb79f814 Fill out descriptions and add link to scales. 2015-11-24 14:06:38 -05:00
wcatron f4ef56993d Add full description text for scales. 2015-11-24 13:36:48 -05:00
Evert Timberg 3bfbf10cff Merge pull request #1689 from wcatron/basic-documentation
Update getting started example code.
2015-11-24 08:03:26 -05:00
Evert Timberg e6ea34e453 Merge pull request #1690 from byCedric/fix/canvas-dimensions-ie10-ie9
Updated retina scale to allow rendering in IE10 and IE9.
2015-11-24 08:00:41 -05:00
Cedric van Putten ae51789c32 Stored pixel ratio in a variable with a fallback value for browsers that doesn't support window.devicePixelRatio fixing rendering issues for IE10 and IE9. (issue #1622) 2015-11-24 11:26:24 +01:00
wcatron 4d48ab5109 Add suggested min and max to documentation. 2015-11-24 02:28:15 -05:00
wcatron c75c21105a Create very simple getting started example code. 2015-11-23 23:59:24 -05:00
Evert Timberg 830cf33c1f Merge pull request #1687 from wcatron/basic-documentation
Converting documentation to tables - radar, polar, and pie
2015-11-23 22:37:04 -05:00
wcatron a0377362d7 Update remainder of tables for radar, polar, and pie. 2015-11-23 19:32:38 -05:00
Evert Timberg 420290969e Merge pull request #1684 from wcatron/basic-documentation
Converting documentation to tables - scales, line, and bar
2015-11-23 18:16:27 -05:00
wcatron dc152f875f Clean up periods and comments. 2015-11-23 12:09:40 -05:00
wcatron a4a07df612 Update options to tables, update example for bar. 2015-11-23 12:03:38 -05:00
Evert Timberg a08f8b3015 Fix typo 2015-11-22 13:26:01 -05:00
Evert Timberg df13f819b5 Merge pull request #1669 from wcatron/basic-documentation
Update getting started documentation default options w/ table.
2015-11-22 13:12:31 -05:00
Evert Timberg a888aba61e Merge pull request #1670 from nnnick/fix/1643
Fixes scatter and bubble chart tooltips
2015-11-21 09:20:58 -05:00
Evert Timberg 800246660a Remove commented code 2015-11-19 21:20:04 -05:00
Evert Timberg ca2e017f80 Update default tooltip configs for scatter charts. Made scatter charts a first class chart type. 2015-11-19 21:15:59 -05:00
Evert Timberg 1471a61609 Update default tooltip callbacks for bubble charts 2015-11-19 21:12:23 -05:00
wcatron 1580d1ed4d Update line chart documentation options to table. 2015-11-19 19:55:12 -05:00
wcatron 34aaeac421 Update getting started documentation default options w/ table. 2015-11-19 16:14:13 -05:00
Evert Timberg 0c69c9a79c Merge pull request #1668 from wcatron/basic-documentation
Updates basic documentation for bar, radar, and doughnut.
2015-11-19 13:39:48 -05:00
wcatron 5400a61ff1 Update doughnut documentation for intiializer and data. 2015-11-19 11:47:47 -05:00
wcatron 942cf5e718 Update Rader initializer and data structure keys. 2015-11-19 11:43:00 -05:00
wcatron f32d62722a Update initializer documentation for Bar. 2015-11-19 11:35:38 -05:00
Evert Timberg 82a74701a7 Merge pull request #1667 from nnnick/fix/pie-legend
Pie and Polar area legend functions
2015-11-18 21:38:52 -05:00
Evert Timberg 09d2f1d900 Merge pull request #1662 from nnnick/fix/string-linear-data
Handle data as strings in numeric scales
2015-11-18 21:35:56 -05:00
etimberg 7edcc0659b Fix polar area legends 2015-11-18 21:30:16 -05:00
etimberg 673e5d59a5 fix pie & doughnut legend 2015-11-18 21:24:49 -05:00
Evert Timberg ead6247cd8 Make sure data is converted to a number in scales when determining min and max. Add tests for this condition to linear, radialLinear, and logarithmic scales. 2015-11-17 18:43:18 -05:00
Evert Timberg e00f9d5790 Fix tests 2015-11-17 18:38:19 -05:00
Tanner Linsley fe77f07c07 Merge pull request #1642 from nnnick/fix/1527
Doughnut, polar area, and radar samples should use the same canvas style
2015-11-16 16:10:24 -07:00
Tanner Linsley 5a80b9e501 Merge pull request #1645 from nnnick/fix/null-callback
Hide lines for which the tick label callback returns null or undefined
2015-11-16 16:10:16 -07:00
Tanner Linsley ae9db841f9 Merge pull request #1646 from nnnick/fix/1640
Can now replace entire chart data object on the fly
2015-11-16 16:10:01 -07:00
Tanner Linsley 937d866bd3 Merge pull request #1647 from nnnick/fix/1324
Fall back to line settings for points if necessary
2015-11-16 16:09:53 -07:00
Tanner Linsley 592414330b Merge pull request #1644 from nnnick/fix/touch-events
Do not bind to touchend events for tooltips
2015-11-16 16:09:41 -07:00
Tanner Linsley ac098b8b2f Merge pull request #1653 from nnnick/fix/1381
Fixes flickering during animations
2015-11-16 16:07:58 -07:00
Evert Timberg 3a193e2117 Update samples 2015-11-15 11:17:02 -05:00
Evert Timberg 0495e45ff7 Can now skip in all cases (start, mid, end) whether or not there is a look 2015-11-15 11:16:41 -05:00
Evert Timberg 045d8f6c2a Keep this as NaN so point._view.skip is set correctly 2015-11-15 11:16:17 -05:00
Evert Timberg 9c78de10ba Fix line tests. Still need to add tests of the skip code. 2015-11-14 23:16:07 -05:00
Evert Timberg 37249e4375 Fix an incorrect test setup 2015-11-14 22:52:10 -05:00
Evert Timberg d61745a311 Handle transitioning NaNs 2015-11-14 22:49:53 -05:00
Evert Timberg 55c7d6872a Prevent NaN results when previous, point, and next are all the same 2015-11-14 22:49:08 -05:00
Evert Timberg 3bd9120a3a some duplicate code cleanup 2015-11-14 22:06:37 -05:00
Evert Timberg 01fe535594 Refactor the lineToNextPoint functionality to give the correct draw line behaviour. Makes the code a little cleaner too. 2015-11-14 21:57:22 -05:00
Evert Timberg f6ac7d9369 Typo 2015-11-13 22:42:42 -05:00
Evert Timberg 0e02d216aa Cleanup 2015-11-13 22:42:33 -05:00
Evert Timberg 108c4fcd56 Simplify code for capping bezier control points. Cap the X direction as well. 2015-11-13 22:15:23 -05:00
Evert Timberg 05523b01b0 Refactor the line drawing code. Tests are broken. 2015-11-13 22:04:38 -05:00
Evert Timberg be07f052d9 Merge pull request #1649 from nnnick/fix/scale_fitting
Improve the fitting of vertical axes
2015-11-13 13:57:00 -05:00
Evert Timberg 7f34d8dd2f Always include padding to ensure that we can always see the tick labels of vertical axes 2015-11-13 13:24:22 -05:00
Evert Timberg f85ffbc09c Use the dataset backgroundColor, borderWidth, and borderColor, if specified, for points. Added tests for this case. 2015-11-13 11:21:44 -05:00
Evert Timberg 6d708a8f2c Update line sample to change the entire data object 2015-11-13 10:01:38 -05:00
Evert Timberg 66bc1dc492 Reference data from the main controller wherever possible. Updated tests to account for this. 2015-11-13 09:38:35 -05:00
Evert Timberg 8e3ba9d88e Update tooltip colour draw code 2015-11-13 08:20:39 -05:00
Evert Timberg 1e4894d625 Test for skipping drawing 2015-11-11 21:49:07 -05:00
Evert Timberg 14b6fdd51e Bail out, same as the x axis 2015-11-11 21:40:29 -05:00
Evert Timberg 3099d967da Do not bind to touchend events. This is the same as v1.x 2015-11-11 21:21:25 -05:00
etimberg 471a5f5aaa Doughnut, polar area, and radar samples should use the same canvas style 2015-11-11 19:06:36 -05:00
Evert Timberg fff13f2692 Merge pull request #1632 from pascoual/v2.0-dev
Fix: no tooltips when missing data for one or more dataset
2015-11-09 19:46:41 -05:00
Pascoual 234efc5267 Fix: tooltips checks indent 2015-11-10 01:00:30 +01:00
Pascoual c4d02a8f96 Fix: no tooltips when missing data for one or more dataset 2015-11-10 00:53:08 +01:00
Tanner Linsley 21efd50fb7 Merge pull request #1628 from nnnick/chrome-travis
Travis CI should also run tests on chrome
2015-11-07 14:00:34 -07:00
Evert Timberg 972ceb24e6 Fix tests 2015-11-07 09:40:41 -05:00
Evert Timberg 679ac764b1 Travis CI should also run tests on chrome 2015-11-07 09:34:07 -05:00
Evert Timberg 962b99e8d3 Merge pull request #1627 from pascoual/v2.0-dev
Add: options.ticks.maxTicksLimit
2015-11-06 19:56:29 -05:00
Pascal Richier 3d15e1ff54 Update doc for options.ticks.maxTicksLimit 2015-11-07 01:46:14 +01:00
Pascal Richier 178880bace Update doc for options.ticks.maxTicksLimit 2015-11-07 01:42:19 +01:00
Pascal Richier d5d63070c6 Add options.ticks.maxTicksLimit
To be able to change default '11' value
2015-11-07 01:39:30 +01:00
Pascal Richier 97da3347be Add options.ticks.maxTicksLimit
To be able to change default '11' value
2015-11-07 01:37:09 +01:00
Evert Timberg d6252df4cd Merge pull request #1601 from nnnick/fix/stacked-bar-line-scale
Fixed stacked scale calculation for combo charts
2015-11-03 18:14:37 -05:00
Evert Timberg 33308616af Merge pull request #1612 from enumag/patch-1
typo
2015-11-03 08:47:43 -05:00
Jáchym Toušek 68255893cf typo 2015-11-03 13:49:34 +01:00
Evert Timberg 57d8155bb0 Merge pull request #1606 from levithomason/patch-1
Fix getting started global chart config typo
2015-11-02 07:29:46 -05:00
Levi Thomason 92841cd38a fix getting started global chart config typo 2015-11-01 23:03:14 -08:00
Derek Perkins 29c3bd3746 Merge pull request #1603 from nnnick/fix-tooltips
Only call custom tooltips when elements have changed.  But be sure to call update internally any time that tooltips need to be redrawn.
2015-11-01 22:52:46 -07:00
Tanner Linsley b0380d4ede Check if dataset is visible when adding active elements to a tooltip 2015-11-01 22:50:16 -07:00
Tanner Linsley 28bc80e439 ElementsAtLabel now returns all datasets' elements at the found index 2015-11-01 22:44:31 -07:00
Tanner Linsley d46524aedc Tooltip's label mode now uses average position of all points 2015-11-01 22:43:44 -07:00
Evert Timberg 677c043a91 Built files 2015-11-01 20:42:13 -05:00
Tanner Linsley 50d9389dce Merge pull request #1604 from nnnick/fix/stacked-bar-x
Fixes bar charts when only Y scale is in stacked mode
2015-11-01 18:36:55 -07:00
Evert Timberg 2c04a816d7 Use correct option to detect stacked mode along x axis. 2015-11-01 20:26:58 -05:00
Tanner Linsley f4a5a30451 Only call custom tooltips when elements have changed. But be sure to call update internally any time that tooltips need to be redrawn. 2015-11-01 13:56:36 -07:00
Evert Timberg 4267d01bc2 Log scale + tests 2015-11-01 09:07:18 -05:00
Evert Timberg 8324b35506 Update linear scale + tests 2015-11-01 08:45:12 -05:00
Derek Perkins b823bae63e Merge pull request #1600 from nnnick/fix-line-stacked-area
Fix line stacked area
2015-10-31 22:48:29 -06:00
Tanner Linsley 334ba44e95 Allow line controller to calculate stacked values 2015-10-31 22:45:25 -06:00
Tanner Linsley e4d308f329 Stacked Area Example 2015-10-31 22:45:11 -06:00
Evert Timberg cf587122da Merge pull request #1586 from nnnick/fix/begin-at-zero-issue-with-constant-data
Scale expansion if min === max will only occur after ticks.beginAtZero is handled
2015-10-31 20:23:57 -04:00
Tanner Linsley 93a79ec470 Commit Built Files 2015-10-31 18:22:52 -06:00
Derek Perkins 3d862962f7 Merge pull request #1599 from nnnick/fix-more-custom-tooltips
Fix more custom tooltips
2015-10-31 18:21:54 -06:00
Tanner Linsley 69bff1183f Better Example 2015-10-31 18:17:52 -06:00
Tanner Linsley 93a923d38f Remove logs 2015-10-31 18:17:42 -06:00
Tanner Linsley 22aabdbfab Update tooltip only when things change (which will only trigger customTooltips when model changes) 2015-10-31 18:17:32 -06:00
Tanner Linsley 5ba1ec0d3b More concise change detection 2015-10-31 18:17:06 -06:00
Tanner Linsley 8398d26d10 Remove Tooltip opacity from core-controller 2015-10-31 18:16:35 -06:00
Tanner Linsley fa33f3158e Don't kill lastActives on chart hover exit 2015-10-31 18:15:58 -06:00
Tanner Linsley 0fa03fad24 Handle opacity in the tooltip update method 2015-10-31 18:14:56 -06:00
Tanner Linsley 91bacf8e51 Commit Built Files 2015-10-31 16:40:23 -06:00
Evert Timberg a848142274 Merge pull request #1597 from nnnick/fix-custom-tooltips
Fix custom tooltips
2015-10-31 18:16:08 -04:00
Tanner Linsley be50c63e72 commas to pass jshint 2015-10-31 16:09:11 -06:00
Tanner Linsley 0494d551b6 Custom Tooltip example now works with the basics 2015-10-31 16:08:55 -06:00
Tanner Linsley ecf5801787 call the custom callback in tooltip options 2015-10-31 16:07:57 -06:00
Tanner Linsley 753fd79bf3 Call tooltip update even when tooltip has no active elements 2015-10-31 16:07:36 -06:00
Tanner Linsley 2845d39311 Merge pull request #1596 from nnnick/fix/v2.0-beta0-tooltips
Improve v2.0.0-beta0 tooltips
2015-10-31 11:23:47 -06:00
Evert Timberg 07b052cfab Tests for suggestedMin and suggestedMax options 2015-10-31 11:40:51 -04:00
etimberg 3aaa3e27f3 suggestedMin and suggestedMax options for scales 2015-10-31 11:01:40 -04:00
etimberg c316f90999 Polar area tooltip improvements 2015-10-30 21:04:45 -04:00
etimberg b8e57144cc Doughnut chart tooltips work 2015-10-30 20:48:31 -04:00
etimberg 1017934dce tooltips for radar charts are working 2015-10-30 20:35:36 -04:00
etimberg 6716dbb7e5 Fix up arguments to tooltip callbacks. Simplified code in some places and removed old code. 2015-10-30 20:12:05 -04:00
etimberg 9bebedd967 Play around with tooltip to see if a better API is possible. No longer crashes for polar area / doughnut / radar charts 2015-10-28 22:52:43 -04:00
etimberg 988034cef6 Scale expansion if min === max will only occur after ticks.beginAtZero is handled 2015-10-27 20:04:21 -04:00
Tanner Linsley 85572d7b67 element.line.js now passes tests 2015-10-26 19:40:52 -06:00
Tanner Linsley 74c04a354a Do not draw line up on first point of line 2015-10-26 19:24:48 -06:00
Tanner Linsley dac859ec1c Rename 01-Scales to 01-Scales.md
Closes #1574
2015-10-26 12:47:37 -06:00
58 arquivos alterados com 3975 adições e 2098 exclusões
+1
Ver Arquivo
@@ -4,6 +4,7 @@ node_js:
- "0.10"
before_install:
- "export CHROME_BIN=chromium-browser"
- "export DISPLAY=:99.0"
- "sh -e /etc/init.d/xvfb start"
externo
+631 -438
Ver Arquivo
Diferenças do arquivo suprimidas por serem muito extensas Carregar Diff
+11 -11
Ver Arquivo
Diff do arquivo suprimido porque uma ou mais linhas são muito longas
+122 -148
Ver Arquivo
@@ -34,9 +34,9 @@ bower install Chart.js --save
npm install Chart.js --save
```
https://cdnjs.com/libraries/chart.js
https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.0.0-beta/Chart.js
###Creating a chart
###Creating a Chart
To create a chart, we need to instantiate the `Chart` class. To do this, we need to pass in the node, jQuery instance, or 2d context of the canvas of where we want to draw the chart. Here's an example.
@@ -48,173 +48,147 @@ To create a chart, we need to instantiate the `Chart` class. To do this, we need
// Any of the following formats may be used
var ctx = document.getElementById("myChart");
var ctx = document.getElementById("myChart").getContext("2d");
var ctx = $("myChart");
var ctx = $("#myChart");
```
Once you have the element or context, you're ready to instantiate a pre-defined chart-type or create your own!
The following example instantiates a the pre-defined Polar Area chart type with a config object of data and options.
```javascript
var myNewChart = Chart.PolarArea(ctx, {
data: data,
options: options
});
```
The following example instantiates a bar chart showing the number of votes for different colors and the y-axis starting at 0.
To create a scatter chart, which is a special configuration of a line chart, we use the following.
```javascript
var myScatterChart = Chart.Scatter(ctx, {
data: data,
options: options
});
```
Alternatively, we can use the more advanced API to create simple or advanced chart types. In the example below, we are creating a line chart.
```javascript
```html
<canvas id="myChart" width="400" height="400"></canvas>
<script>
var ctx = document.getElementById("myChart");
var myChart = new Chart(ctx, {
type: 'line', // built in types are 'line', 'bar', 'radar', 'polarArea', 'doughnut', 'scatter'
data: data,
options: options
type: 'bar',
data: {
labels: ["Red", "Blue", "Yellow", "Green", "Purple", "Orange"],
datasets: [{
label: '# of Votes',
data: [12, 19, 3, 5, 2, 3]
}]
},
options:{
scales:{
yAxes:[{
ticks:{
beginAtZero:true
}
}]
}
}
});
</script>
```
It's that easy to get started using Chart.js! From here you can explore the many options that can help you customise your charts with scales, tooltips, labels, colors, custom actions, and much more.
###Global chart configuration
This concept was introduced in Chart.js 1.0 to keep configuration DRY, and allow for changing options globally across chart types, avoiding the need to specify options for each instance, or the default for a particular chart type.
Chart.js merges configurations and options in a few places with the global defaults using chart type defaults and scales defaults. This way you can be as specific as you want in your individual chart configs, or change the defaults for Chart.js as a whole.
```javascript
Chart.defaults.global = {
responsive: true,
responsiveAnimationDuration: 0,
maintainAspectRatio: true,
events: ["mousemove", "mouseout", "click", "touchstart", "touchmove", "touchend"],
hover: {
onHover: null,
mode: 'single',
animationDuration: 400,
},
onClick: null,
defaultColor: 'rgba(0,0,0,0.1)',
The global options are defined in `Chart.defaults.global`.
// Element defaults defined in element extensions
elements: {},
Name | Type | Default | Description
--- | --- | --- | ---
responsive | Boolean | true | Resizes when the canvas container does.
responsiveAnimationDuration | Number | 0 | Duration in milliseconds it takes to animate to new size after a resize event.
maintainAspectRatio | Boolean | true | Maintain the original canvas aspect ratio `(width / height)` when resizing
events | Array[String] | `["mousemove", "mouseout", "click", "touchstart", "touchmove", "touchend"]` | Events that the chart should listen to for tooltips and hovering
hover |-|-|-
*hover*.onHover | Function | null | Called when any of the events fire. Called in the context of the chart and passed an array of active elements (bars, points, etc)
*hover*.mode | String | 'single' | Sets which elements hover. Acceptable options are `'single'`, `'label'`, or `'dataset'`. `single` highlights the closest element. `label` highlights elements in all datasets at the same `X` value. `dataset` highlights the closest dataset.
*hover*.animationDuration | Number | 400 | Duration in milliseconds it takes to animate hover style changes
onClick | Function | null | Called if the event is of type 'mouseup' or 'click'. Called in the context of the chart and passed an array of active elements
defaultColor | Color | 'rgba(0,0,0,0.1)' |
legendCallback | Function | ` function (chart) { // the chart object to generate a legend from. }` | Function to generate a legend. Default implementation returns an HTML string.
// Legend callback function.
// @param {Chart} chart : the chart object to generate a legend for
legendCallback: legendCallback: function(chart) {
var text = [];
text.push('<ul class="' + chart.id + '-legend">');
for (var i = 0; i < chart.data.datasets.length; i++) {
text.push('<li><span style="background-color:' + chart.data.datasets[i].backgroundColor + '">');
if (chart.data.datasets[i].label) {
text.push(chart.data.datasets[i].label);
}
text.push('</span></li>');
}
text.push('</ul>');
The global options for tooltips are defined in `Chart.defaults.global.tooltips`.
return text.join("");
}
Name | Type | Default | Description
--- |:---:| --- | ---
enabled | Boolean | true |
custom | | null |
mode | String | 'single' | Sets which elements appear in the tooltip. Acceptable options are `'single'` or `'label'`. `single` highlights the closest element. `label` highlights elements in all datasets at the same `X` value.
backgroundColor | Color | 'rgba(0,0,0,0.8)' | Background color of the tooltip
| | |
Label | | | There are three labels you can control. `title`, `body`, `footer` the star (\*) represents one of these three. *(i.e. titleFontFamily, footerSpacing)*
\*FontFamily | String | "'Helvetica Neue', 'Helvetica', 'Arial', sans-serif" |
\*FontSize | Number | 12 |
\*FontStyle | String | title - "bold", body - "normal", footer - "bold" |
\*Spacing | Number | 2 |
\*Color | Color | "#fff" |
\*Align | String | "left" | text alignment. See [MDN Canvas Documentation](https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/textAlign)
titleMarginBottom | Number | 6 | Margin to add on bottom of title section
footerMarginTop | Number | 6 | Margin to add before drawing the footer
xPadding | Number | 6 | Padding to add on top and bottom of tooltip
yPadding | Number | 6 | Padding to add on left and right of tooltip
caretSize | Number | 5 | Size, in px, of the tooltip arrow
cornerRadius | Number | 6 | Radius of tooltip corner curves
xOffset | Number | 10 |
multiKeyBackground | Color | "#fff" |
| | |
callbacks | - | - | V2.0 introduces callback functions as a replacement for the template engine in v1. The tooltip has the following callbacks for providing text. For all functions, 'this' will be the tooltip object create from the Chart.Tooltip constructor
**Callback Functions** | | | All functions are called with the same arguments
xLabel | String or Array[Strings] | | This is the xDataValue for each item to be displayed in the tooltip
yLabel | String or Array[Strings] | | This is the yDataValue for each item to be displayed in the tooltip
index | Number | | Data index.
data | Object | | Data object passed to chart.
`return`| String or Array[Strings] | | All functions must return either a string or an array of strings. Arrays of strings are treated as multiple lines of text.
| | |
*callbacks*.beforeTitle | Function | none | Text to render before the title
*callbacks*.title | Function | `function(tooltipItems, data) { //Pick first xLabel }` | Text to render as the title
*callbacks*.afterTitle | Function | none | Text to render after the ttiel
*callbacks*.beforeBody | Function | none | Text to render before the body section
*callbacks*.beforeLabel | Function | none | Text to render before an individual label
*callbacks*.label | Function | `function(tooltipItem, data) { // Returns "datasetLabel: tooltipItem.yLabel" }` | Text to render as label
*callbacks*.afterLabel | Function | none | Text to render after an individual label
*callbacks*.afterBody | Function | none | Text to render after the body section
*callbacks*.beforeFooter | Function | none | Text to render before the footer section
*callbacks*.footer | Function | none | Text to render as the footer
*callbacks*.afterFooter | Function | none | Text to render after the footer section
animation: {
duration: 1000,
easing: "easeOutQuart",
onProgress: function() {},
onComplete: function() {},
},
The global options for animations are defined in `Chart.defaults.global.animation`.
tooltips:{
enabled: true,
custom: null,
backgroundColor: "rgba(0,0,0,0.8)",
fontFamily: "'Helvetica Neue', 'Helvetica', 'Arial', sans-serif",
fontSize: 10,
fontStyle: "normal",
fontColor: "#fff",
titleFontFamily: "'Helvetica Neue', 'Helvetica', 'Arial', sans-serif",
titleFontSize: 12,
titleFontStyle: "bold",
titleFontColor: "#fff",
yPadding: 6,
xPadding: 6,
caretSize: 8,
cornerRadius: 6,
xOffset: 10,
// V2.0 introduces callback functions as a replacement for the template engine in v1. The tooltip
// has the following callbacks for providing text. For all functions, 'this' will be the tooltip object
// create from the Chart.Tooltip constructor
//
// All functions are called with the same arguments
// - xLabel : string or array of strings. This is the xDataValue for each item to be displayed in the tooltip
// - yLabel : string or array of strings. This is the yDataValue for each item to be displayed in the tooltip
// - index : number. Data index
// - datasetIndex : number. Dataset index
// - data : object. Data object passed to chart
callbacks: {
beforeTitle: helpers.noop,
title: function(xLabel, yLabel, index, datasetIndex, data) {
// If there are multiple items, use the xLabel of the
return helpers.isArray(xLabel) ? xLabel[0] : xLabel;
},
afterTitle: helpers.noop,
Name | Type | Default | Description
--- |:---:| --- | ---
duration | Number | 1000 | The number of milliseconds an animation takes.
easing | String | "easeOutQuart" | Easing function to use.
onProgress | Function | none |
onComplete | Function |none |
beforeBody: helpers.noop,
The global options for elements are defined in `Chart.defaults.global.elements`.
beforeLabel: helpers.noop,
label: function(xLabel, yLabel, index, datasetIndex, data) {
return this._data.datasets[datasetIndex].label + ': ' + yLabel;
},
afterLabel: helpers.noop,
afterBody: helpers.noop,
beforeFooter: helpers.noop,
footer: helpers.noop,
afterFooter: helpers.noop,
},
multiKeyBackground: '#fff',
},
elements: {
arc: {
backgroundColor: Chart.defaults.global.defaultColor,
borderColor: "#fff",
borderWidth: 2
},
line: {
tension: 0.4,
backgroundColor: Chart.defaults.global.defaultColor,
borderWidth: 3,
borderColor: Chart.defaults.global.defaultColor,
borderCapStyle: 'butt',
borderDash: [],
borderDashOffset: 0.0,
borderJoinStyle: 'miter',
fill: true, // do we fill in the area between the line and its base axis
skipNull: true,
drawNull: false,
},
point: {
radius: 3,
backgroundColor: Chart.defaults.global.defaultColor,
borderWidth: 1,
borderColor: Chart.defaults.global.defaultColor,
// Hover
hitRadius: 1,
hoverRadius: 4,
hoverBorderWidth: 1,
},
rectangle: {
backgroundColor: Chart.defaults.global.defaultColor,
borderWidth: 0,
borderColor: Chart.defaults.global.defaultColor,
}
}
}
```
Name | Type | Default | Description
--- |:---:| --- | ---
arc | - | - | -
*arc*.backgroundColor | Color | `Chart.defaults.global.defaultColor` | Default fill color for arcs
*arc*.borderColor | Color | "#fff" | Default stroke color for arcs
*arc*.borderWidth | Number | 2 | Default stroke width for arcs
line | - | - | -
*line*.tension | Number | 0.4 | Default bezier curve tension. Set to `0` for no bezier curves.
*line*.backgroundColor | Color | `Chart.defaults.global.defaultColor` | Default line fill color
*line*.borderWidth | Number | 3 | Default line stroke width
*line*.borderColor | Color | `Chart.defaults.global.defaultColor` | Default line stroke color
*line*.borderCapStyle | String | 'butt' | Default line cap style. See [MDN](https://developer.mozilla.org/en/docs/Web/API/CanvasRenderingContext2D/lineCap)
*line*.borderDash | Array | `[]` | Default line dash. See [MDN](https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/setLineDash)
*line*.borderDashOffset | Number | 0.0 | Default line dash offset. See [MDN](https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/lineDashOffset)
*line*.borderJoinStyle | String | 'miter' | Default line join style. See [MDN](https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/lineJoin)
*line*.fill | Boolean | true |
point | - | - | -
*point*.radius | Number | 3 | Default point radius
*point*.backgroundColor | Color | `Chart.defaults.global.defaultColor` | Default point fill color
*point*.borderWidth | Number | 1 | Default point stroke width
*point*.borderColor | Color | `Chart.defaults.global.defaultColor` | Default point stroke color
*point*.hitRadius | Number | 1 | Extra radius added to point radius for hit detection
*point*.hoverRadius | Number | 4 | Default point radius when hovered
*point*.hoverBorderWidth | Number | 1 | Default stroke width when hovered
rectangle | - | - | -
*rectangle*.backgroundColor | Color | `Chart.defaults.global.defaultColor` | Default bar fill color
*rectangle*.borderWidth | Number | 0 | Default bar stroke width
*rectangle*.borderColor | Color | `Chart.defaults.global.defaultColor` | Default bar stroke color
If for example, you wanted all charts created to be responsive, and resize when the browser window does, the following setting can be changed:
@@ -222,4 +196,4 @@ If for example, you wanted all charts created to be responsive, and resize when
Chart.defaults.global.responsive = true;
```
Now, every time we create a chart, `options.responsive` will be `true`.
Now, every time we create a chart, `options.responsive` will be `true`.
-227
Ver Arquivo
@@ -1,227 +0,0 @@
---
title: Getting started
anchor: getting-started
---
###Scales
Scales in v2.0 of Chart.js are significantly more powerful, but also different than those of v1.0.
- Multiple x & y axes are now supported.
- A built-in label auto-skip feature now detects would-be overlapping ticks and labels and removes every nth label to keep things displaying normally.
- Scale labels
Every scale extends a core scale class with the following options:
```javascript
Chart.defaults.scale = {
display: true,
// grid line settings
gridLines: {
show: true,
color: "rgba(0, 0, 0, 0.1)",
lineWidth: 1,
drawOnChartArea: true,
drawTicks: true,
zeroLineWidth: 1,
zeroLineColor: "rgba(0,0,0,0.25)",
offsetGridLines: false,
},
// scale label
scaleLabel: {
fontColor: '#666',
fontFamily: 'Helvetica Neue',
fontSize: 12,
fontStyle: 'normal',
// actual label
labelString: '',
// display property
show: false,
},
// label settings
ticks: {
beginAtZero: false,
fontSize: 12,
fontStyle: "normal",
fontColor: "#666",
fontFamily: "Helvetica Neue",
maxRotation: 90,
minRotation: 20,
mirror: false,
padding: 10,
reverse: false,
show: true,
template: "<%=value%>",
userCallback: false,
},
};
```
The `userCallback` method may be used for advanced tick customization. The following callback would display every label in scientific notation
```javascript
{
scales: {
xAxes: [{
ticks: {
// Return an empty string to draw the tick line but hide the tick label
// Return `null` or `undefined` to hide the tick line entirely
userCallback: function(value, index, values) {
return value.toExponential();
}
}
}]
}
}
```
#### Category Scale
The category scale will be familiar to those who have used v1.0. Labels are drawn in from the labels array included in the chart data.
The category scale extends the core scale class with the following tick template:
```javascript
{
position: "bottom",
}
```
#### Linear Scale
The linear scale can be used to display numerical data. It can be placed on either the x or y axis. The scatter chart type automatically configures a line chart to use one of these scales for the x axis.
The linear scale extends the core scale class with the following tick template:
```javascript
{
position: "left",
}
```
#### Logarithmic Scale
The logarithmic scale is used to display logarithmic data of course. It can be placed on either the x or y axis.
The log scale extends the core scale class with the following tick template:
```javascript
{
position: "left",
ticks: {
template: "<%var remain = value / (Math.pow(10, Math.floor(Chart.helpers.log10(value))));if (remain === 1 || remain === 2 || remain === 5) {%><%=value.toExponential()%><%} else {%><%= null %><%}%>",
}
}
```
#### Time Scale
The time scale is used to display times and dates. It can be placed on the x axis. When building its ticks, it will automatically calculate the most comfortable unit base on the size of the scale.
The time scale extends the core scale class with the following tick template:
```javascript
{
position: "bottom",
time: {
// string/callback - By default, date objects are expected. You may use a pattern string from http://momentjs.com/docs/#/parsing/string-format/ to parse a time string format, or use a callback function that is passed the label, and must return a moment() instance.
format: false,
// string - By default, unit will automatically be detected. Override with 'week', 'month', 'year', etc. (see supported time measurements)
unit: false,
// string - By default, no rounding is applied. To round, set to a supported time unit eg. 'week', 'month', 'year', etc.
round: false,
// string - By default, is set to the detected (or manually overridden) time unit's `display` property (see supported time measurements). To override, use a pattern string from http://momentjs.com/docs/#/displaying/format/
displayFormat: false
},
}
```
The following time measurements are supported:
```javascript
{
'millisecond': {
display: 'SSS [ms]', // 002 ms
maxStep: 1000,
},
'second': {
display: 'h:mm:ss a', // 11:20:01 AM
maxStep: 60,
},
'minute': {
display: 'h:mm:ss a', // 11:20:01 AM
maxStep: 60,
},
'hour': {
display: 'MMM D, hA', // Sept 4, 5PM
maxStep: 24,
},
'day': {
display: 'll', // Sep 4 2015
maxStep: 7,
},
'week': {
display: 'll', // Week 46, or maybe "[W]WW - YYYY" ?
maxStep: 4.3333,
},
'month': {
display: 'MMM YYYY', // Sept 2015
maxStep: 12,
},
'quarter': {
display: '[Q]Q - YYYY', // Q3
maxStep: 4,
},
'year': {
display: 'YYYY', // 2015
maxStep: false,
},
}
```
#### Radial Linear Scale
The radial linear scale is used specifically for the radar chart type.
The radial linear scale extends the core scale class with the following tick template:
```javascript
{
animate: true,
lineArc: false,
position: "chartArea",
angleLines: {
show: true,
color: "rgba(0, 0, 0, 0.1)",
lineWidth: 1
},
// label settings
ticks: {
//Boolean - Show a backdrop to the scale label
showLabelBackdrop: true,
//String - The colour of the label backdrop
backdropColor: "rgba(255,255,255,0.75)",
//Number - The backdrop padding above & below the label in pixels
backdropPaddingY: 2,
//Number - The backdrop padding to the side of the label in pixels
backdropPaddingX: 2,
},
pointLabels: {
//String - Point label font declaration
fontFamily: "'Arial'",
//String - Point label font weight
fontStyle: "normal",
//Number - Point label font size in pixels
fontSize: 10,
//String - Point label font colour
fontColor: "#666",
},
}
```
+262
Ver Arquivo
@@ -0,0 +1,262 @@
---
title: Getting started
anchor: scales
---
###Scales
Scales in v2.0 of Chart.js are significantly more powerful, but also different than those of v1.0.
- Multiple x & y axes are now supported.
- A built-in label auto-skip feature now detects would-be overlapping ticks and labels and removes every nth label to keep things displaying normally.
- Scale titles are now supported
Every scale extends a core scale class with the following options:
Name | Type | Default | Description
--- |:---:| --- | ---
type | String | Chart specific. | Type of scale being employed. Custom scales can be created and registered with a string key. Options: ["category"](#scales-category-scale), ["linear"](#scales-linear-scale), ["logarithmic"](#scales-logarithmic-scale), ["time"](#scales-time-scale), ["radialLinear"](#scales-radial-linear-scale)
display | Boolean | true | If true, show the scale including gridlines, ticks, and labels. Overrides *gridLines.display*, *scaleLabel.display*, and *ticks.display*.
**gridLines** | Array | - | Options for the grid lines that run perpendicular to the axis.
*gridLines*.display | Boolean | true |
*gridLines*.color | Color | "rgba(0, 0, 0, 0.1)" | Color of the grid lines.
*gridLines*.lineWidth | Number | 1 | Stroke width of grid lines
*gridLines*.drawOnChartArea | Boolean | true | If true, draw lines on the chart area inside the axis lines. This is useful when there are multiple axes and you need to control which grid lines are drawn
*gridLines*.drawTicks | Boolean | true | If true, draw lines beside the ticks in the axis area beside the chart.
*gridLines*.zeroLineWidth | Number | 1 | Stroke width of the grid line for the first index (index 0).
*gridLines*.zeroLineColor | Color | "rgba(0, 0, 0, 0.25)" | Stroke color of the grid line for the first index (index 0).
*gridLines*.offsetGridLines | Boolean | false | If true, offset labels from grid lines.
**scaleLabel** | Array | | Title for the entire axis.
*scaleLabel*.display | Boolean | false |
*scaleLabel*.labelString | String | "" | The text for the title. (i.e. "# of People", "Response Choices")
*scaleLabel*.fontColor | Color | "#666" | Font color for the scale title.
*scaleLabel*.fontFamily| String | "Helvetica Neue" | Font family for the scale title, follows CSS font-family options.
*scaleLabel*.fontSize | Number | 12 | Font size for the scale title.
*scaleLabel*.fontStyle | String | "normal" | Font style for the scale title, follows CSS font-style options (i.e. normal, italic, oblique, initial, inherit).
**ticks** | Array | | Settings for the labels that run along the axis.
*ticks*.beginAtZero | Boolean | false | If true the scale will be begin at 0, if false the ticks will begin at your smallest data value.
*ticks*.fontColor | Color | "#666" | Font color for the tick labels.
*ticks*.fontFamily | String | "Helvetica Neue" | Font family for the tick labels, follows CSS font-family options.
*ticks*.fontSize | Number | 12 | Font size for the tick labels.
*ticks*.fontStyle | String | "normal" | Font style for the tick labels, follows CSS font-style options (i.e. normal, italic, oblique, initial, inherit).
*ticks*.maxRotation | Number | 90 | Maximum rotation for tick labels when rotating to condense labels. Note: Rotation doesn't occur until necessary. *Note: Only applicable to horizontal scales.*
*ticks*.minRotation | Number | 20 | *currently not-implemented* Minimum rotation for tick labels when condensing is necessary. *Note: Only applicable to horizontal scales.*
*ticks*.padding | Number | 10 | Padding between the tick label and the axis. *Note: Only applicable to horizontal scales.*
*ticks*.mirror | Boolean | false | Flips tick labels around axis, displaying the labels inside the chart instead of outside. *Note: Only applicable to vertical scales.*
*ticks*.reverse | Boolean | false | Reverses order of tick labels.
*ticks*.display | Boolean | true | If true, show the ticks.
*ticks*.suggestedMin | Number | - | User defined minimum number for the scale, overrides minimum value *except for if* it is higher than the minimum value.
*ticks*.suggestedMax | Number | - | User defined maximum number for the scale, overrides maximum value *except for if* it is lower than the maximum value.
*ticks*.callback | Function | `function(value) { return '' + value; } ` | Returns the string representation of the tick value as it should be displayed on the chart.
The `callback` method may be used for advanced tick customization. The following callback would display every label in scientific notation
```javascript
{
scales: {
xAxes: [{
ticks: {
// Return an empty string to draw the tick line but hide the tick label
// Return `null` or `undefined` to hide the tick line entirely
userCallback: function(value, index, values) {
return value.toExponential();
}
}
}]
}
}
```
#### Category Scale
The category scale will be familiar to those who have used v1.0. Labels are drawn in from the labels array included in the chart data.
The category scale extends the core scale class with the following tick template:
```javascript
{
position: "bottom",
}
```
#### Linear Scale
The linear scale can be used to display numerical data. It can be placed on either the x or y axis. The scatter chart type automatically configures a line chart to use one of these scales for the x axis.
The linear scale extends the core scale class with the following tick template:
```javascript
{
position: "left",
ticks: {
callback: function(tickValue, index, ticks) {
var delta = ticks[1] - ticks[0];
// If we have a number like 2.5 as the delta, figure out how many decimal places we need
if (Math.abs(delta) > 1) {
if (tickValue !== Math.floor(tickValue)) {
// not an integer
delta = tickValue - Math.floor(tickValue);
}
}
var logDelta = helpers.log10(Math.abs(delta));
var tickString = '';
if (tickValue !== 0) {
var numDecimal = -1 * Math.floor(logDelta);
numDecimal = Math.max(Math.min(numDecimal, 20), 0); // toFixed has a max of 20 decimal places
tickString = tickValue.toFixed(numDecimal);
} else {
tickString = '0'; // never show decimal places for 0
}
return tickString;
}
}
}
```
#### Logarithmic Scale
The logarithmic scale is used to display logarithmic data of course. It can be placed on either the x or y axis.
The log scale extends the core scale class with the following tick template:
```javascript
{
position: "left",
ticks: {
callback: function(value) {
var remain = value / (Math.pow(10, Math.floor(Chart.helpers.log10(value))));
if (remain === 1 || remain === 2 || remain === 5) {
return value.toExponential();
} else {
return '';
}
}
}
}
```
#### Time Scale
The time scale is used to display times and dates. It can be placed on the x axis. When building its ticks, it will automatically calculate the most comfortable unit base on the size of the scale.
The time scale extends the core scale class with the following tick template:
```javascript
{
position: "bottom",
time: {
// string/callback - By default, date objects are expected. You may use a pattern string from http://momentjs.com/docs/#/parsing/string-format/ to parse a time string format, or use a callback function that is passed the label, and must return a moment() instance.
format: false,
// string - By default, unit will automatically be detected. Override with 'week', 'month', 'year', etc. (see supported time measurements)
unit: false,
// string - By default, no rounding is applied. To round, set to a supported time unit eg. 'week', 'month', 'year', etc.
round: false,
// Moment js for each of the units. Replaces `displayFormat`
// To override, use a pattern string from http://momentjs.com/docs/#/displaying/format/
displayFormats: {
'millisecond': 'SSS [ms]',
'second': 'h:mm:ss a', // 11:20:01 AM
'minute': 'h:mm:ss a', // 11:20:01 AM
'hour': 'MMM D, hA', // Sept 4, 5PM
'day': 'll', // Sep 4 2015
'week': 'll', // Week 46, or maybe "[W]WW - YYYY" ?
'month': 'MMM YYYY', // Sept 2015
'quarter': '[Q]Q - YYYY', // Q3
'year': 'YYYY', // 2015
},
},
}
```
The following time measurements are supported:
```javascript
{
'millisecond': {
display: 'SSS [ms]', // 002 ms
maxStep: 1000,
},
'second': {
display: 'h:mm:ss a', // 11:20:01 AM
maxStep: 60,
},
'minute': {
display: 'h:mm:ss a', // 11:20:01 AM
maxStep: 60,
},
'hour': {
display: 'MMM D, hA', // Sept 4, 5PM
maxStep: 24,
},
'day': {
display: 'll', // Sep 4 2015
maxStep: 7,
},
'week': {
display: 'll', // Week 46, or maybe "[W]WW - YYYY" ?
maxStep: 4.3333,
},
'month': {
display: 'MMM YYYY', // Sept 2015
maxStep: 12,
},
'quarter': {
display: '[Q]Q - YYYY', // Q3
maxStep: 4,
},
'year': {
display: 'YYYY', // 2015
maxStep: false,
},
}
```
#### Radial Linear Scale
The radial linear scale is used specifically for the radar chart type.
The radial linear scale extends the core scale class with the following tick template:
```javascript
{
animate: true,
lineArc: false,
position: "chartArea",
angleLines: {
display: true,
color: "rgba(0, 0, 0, 0.1)",
lineWidth: 1
},
// label settings
ticks: {
//Boolean - Show a backdrop to the scale label
showLabelBackdrop: true,
//String - The colour of the label backdrop
backdropColor: "rgba(255,255,255,0.75)",
//Number - The backdrop padding above & below the label in pixels
backdropPaddingY: 2,
//Number - The backdrop padding to the side of the label in pixels
backdropPaddingX: 2,
//Number - Limit the maximum number of ticks
maxTicksLimit: 11,
},
pointLabels: {
//String - Point label font declaration
fontFamily: "'Arial'",
//String - Point label font weight
fontStyle: "normal",
//Number - Point label font size in pixels
fontSize: 10,
//String - Point label font colour
fontColor: "#666",
},
}
```
+24 -55
Ver Arquivo
@@ -15,7 +15,7 @@ Often, it is used to show trend data, and the comparison of two data sets.
```javascript
var myLineChart = new Chart(ctx, {
type: 'line',
data: data,
data: data,
options: options
});
```
@@ -23,7 +23,7 @@ var myLineChart = new Chart(ctx, {
Alternatively a line chart can be created using syntax similar to the v1.0 syntax
```javascript
var myLineChart = Chart.Line(ctx, {
data: data,
data: data,
options: options
});
```
@@ -113,37 +113,22 @@ The label key on each dataset is optional, and can be used when generating a sca
These are the customisation options specific to Line charts. These options are merged with the [global chart configuration options](#getting-started-global-chart-configuration), and form the options of the chart.
```javascript
{
// Boolean - if true, line stack on top of each other along the y axis
stacked: false,
The default options for line chart are defined in `Chart.defaults.Line`.
hover: {
// String - We use a label hover mode since the x axis displays data by the index in the dataset
mode: "label"
},
scales: {
// Defines all of the x axes used in the chart. See the [scale documentation](#getting-started-scales) for details on the available options
xAxes: [{
// String - type of scale. Built in types are 'category' and 'linear'
type: 'category',
// String - id of the axis so that data can bind to it
id: "x-axis-1", // need an ID so datasets can reference the scale
}],
// Defines all of the y axes used in the chart.
// By default, the line chart uses a linear scale along the y axis
yAxes: [{
type: 'linear',
// String - ID of the axis for data binding
id: "y-axis-1",
}],
}
};
```
Name | Type | Default | Description
--- | --- | --- | ---
stacked | Boolean | false | If true, lines stack on top of each other along the y axis.
*hover*.mode | String | "label" | Label's hover mode. "label" is used since the x axis displays data by the index in the dataset.
scales | - | - | -
*scales*.xAxes | Array | `[{type:"category","id":"x-axis-1"}]` | Defines all of the x axes used in the chart. See the [scale documentation](#getting-started-scales) for details on the available options.
*Options for xAxes* | | |
type | String | "category" | As defined in ["Category"](#scales-category-scale).
id | String | "x-axis-1" | Id of the axis so that data can bind to it.
| | |
*scales*.yAxes | Array | `[{type:"linear","id":"y-axis-1"}]` | Defines all of the x axes used in the chart. See the [scale documentation](#getting-started-scales) for details on the available options.
*Options for yAxes* | | |
type | String | "linear" | As defined in ["Linear"](#scales-linear-scale).
id | String | "y-axis-1" | Id of the axis so that data can bind to it.
You can override these for your `Chart` instance by passing a member `options` into the `Line` method.
@@ -152,10 +137,10 @@ For example, we could have a line chart display without an x axis by doing the f
```javascript
new Chart(ctx, {
type: 'line',
data: data,
data: data,
options: {
xAxes: [{
show: false
display: false
}]
}
});
@@ -181,32 +166,16 @@ canvas.onclick = function(evt){
This functionality may be useful for implementing DOM based tooltips, or triggering custom behaviour in your application.
#### .getElementAtEvent( event )
Calling `getElementAtEvent(event)` on your Chart instance passing an argument of an event, or jQuery event, will return the single element at the event position. If there are multiple items within range, only the first is returned
#### .update( )
Calling `update()` on your Chart instance will re-render the chart with any updated values, allowing you to edit the value of multiple existing points, then render those in one animated render loop.
Calling `update()` on your Chart instance will re-render the chart with any updated values, allowing you to edit the value of multiple existing points, then render those in one animated render loop. You can safely call `update()` after changing the entire data object on the chart.
```javascript
myLineChart.datasets[0].points[2].value = 50;
myLineChart.data.datasets[0].data[2] = 50;
// Would update the first dataset's value of 'March' to be 50
myLineChart.update();
// Calling update now animates the position of March from 90 to 50.
```
#### .addData( valuesArray, label )
Calling `addData(valuesArray, label)` on your Chart instance passing an array of values for each dataset, along with a label for those points.
```javascript
// The values array passed into addData should be one for each dataset in the chart
myLineChart.addData([40, 60], "August");
// This new data will now animate at the end of the chart.
```
#### .removeData( )
Calling `removeData()` on your Chart instance will remove the first value for all datasets on the chart.
```javascript
myLineChart.removeData();
// The chart will remove the first point and animate other points into place
```
+77 -177
Ver Arquivo
@@ -14,8 +14,9 @@ It is sometimes used to show trend data, and the comparison of multiple data set
### Example usage
```javascript
var myBarChart = new Chart(ctx).Bar({
data: data,
var myBarChart = new Chart(ctx,{
type: 'bar',
data: data,
options: options
});
```
@@ -72,212 +73,111 @@ The label key on each dataset is optional, and can be used when generating a sca
These are the customisation options specific to Bar charts. These options are merged with the [global chart configuration options](#getting-started-global-chart-configuration), and form the options of the chart.
```javascript
{
// Boolean - if true, bars stack on top of each other
stacked: false,
The default options for bar chart are defined in `Chart.defaults.Bar`.
hover: {
// String - We use a label hover mode since the x axis displays data by the index in the dataset
mode: "label"
},
scales: {
// The bar chart officially supports only 1 x-axis but uses an array to keep the API consistent. Use a scatter chart if you need multiple x axes.
xAxes: [{
// String - type of axis to use. Should not be changed from 'dataset'.
scaleType: "dataset", // scatter should not use a dataset axis
// Boolean - if true, show the scale
display: true,
// String - position of the scale. possible options are "top" and "bottom" for dataset scales
position: "bottom",
// String - id of the axis so that data can bind to it
id: "x-axis-1", // need an ID so datasets can reference the scale
// grid line settings
gridLines: {
// Boolean - if true, show the grid lines
show: true,
// String - color of the grid lines
color: "rgba(0, 0, 0, 0.05)",
// Number - width of the grid lines
lineWidth: 1,
// Boolean - if true draw lines on the chart area
drawOnChartArea: true,
// Boolean - if true draw ticks in the axis area
drawTicks: true,
// Number - width of the grid line for the first index (index 0)
zeroLineWidth: 1,
// String - color of the grid line for the first index
zeroLineColor: "rgba(0,0,0,0.25)",
// Boolean - if true, offset labels from grid lines
offsetGridLines: false,
},
// label settings
labels: {
// Boolean - if true show labels
show: true,
// String - template string for labels
template: "<%=value%>",
// Number - label font size
fontSize: 12,
// String - label font style
fontStyle: "normal",
// String - label font color
fontColor: "#666",
// String - label font family
fontFamily: "Helvetica Neue",
},
}],
yAxes: [{
// String - type of axis. 'linear' is the default but extensions may provide other types such as logarithmic
scaleType: "linear",
// Boolean - if true, show the scale
display: true,
// String - position of axis. Vertical axes can have either "left" or "right"
position: "left",
// ID of the axis for data binding
id: "y-axis-1",
// grid line settings
gridLines: {
// Boolean - if true, show the grid lines
show: true,
// String - color of the grid lines
color: "rgba(0, 0, 0, 0.05)",
// Number - width of the grid lines
lineWidth: 1,
// Boolean - if true draw lines on the chart area
drawOnChartArea: true,
// Boolean - if true draw ticks in the axis area
drawTicks: true,
// Number - width of the grid line representing a numerical value of 0
zeroLineWidth: 1,
// String - color of the grid line representing a numerical value of 0
zeroLineColor: "rgba(0,0,0,0.25)",
},
// Boolean - if true ensures that the scale always has a 0 point
beginAtZero: false,
// Object - if specified, allows the user to override the step generation algorithm.
// Contains the following values
// start: // number to start at
// stepWidth: // size of step
// steps: // number of steps
override: null,
// label settings
labels: {
// Boolean - if true show labels
show: true,
// String - template string for labels
template: "<%=value%>",
// Function - if specified this is passed the tick value, index, and the array of all tick values. Returns a string that is used as the label for that value
userCallback: null,
// Number - label font size
fontSize: 12,
// String - label font style
fontStyle: "normal",
// String - label font color
fontColor: "#666",
// String - label font family
fontFamily: "Helvetica Neue",
},
}],
},
};
```
Name | Type | Default | Description
--- |:---:| --- | ---
stacked | Boolean | false |
*hover*.mode | String | "label" | Label's hover mode. "label" is used since the x axis displays data by the index in the dataset.
scales | Array | - | -
*scales*.xAxes | Array | | The bar chart officially supports only 1 x-axis but uses an array to keep the API consistent. Use a scatter chart if you need multiple x axes.
*Options for xAxes* | | |
type | String | "Category" | As defined in [Scales](#scales-category-scale).
display | Boolean | true | If true, show the scale.
position | String | "bottom" | Position of the scale. Options are "top" and "bottom" for dataset scales.
id | String | "x-axis-1" | Id of the axis so that data can bind to it
categoryPercentage | Number | 0.8 | Percent (0-1) of the available width (the space between the gridlines for small datasets) for each data-point to use for the bars. [Read More](#bar-chart-barpercentage-vs-categorypercentage)
barPercentage | Number | 0.9 | Percent (0-1) of the available width each bar should be within the category percentage. 1.0 will take the whole category width and put the bars right next to each other. [Read More](#bar-chart-barpercentage-vs-categorypercentage)
gridLines | Array | [See Scales](#scales) |
*gridLines*.offsetGridLines | Boolean | true | If true, the bars for a particular data point fall between the grid lines. If false, the grid line will go right down the middle of the bars.
scaleLabel | Array | [See Scales](#scales) |
ticks | Array | [See Scales](#scales) |
| | |
*scales*.yAxes | Array | `[{ type: "linear" }]` |
*Options for xAxes* | | |
type | String | "linear" | As defined in [Scales](#scales-linear-scale).
display | Boolean | true | If true, show the scale.
position | String | "left" | Position of the scale. Options are "left" and "right" for dataset scales.
id | String | "y-axis-1" | Id of the axis so that data can bind to it.
gridLines | Array | [See Scales](#scales) |
scaleLabel | Array | [See Scales](#scales) |
ticks | Array | [See Scales](#scales) |
You can override these for your `Chart` instance by passing a second argument into the `Bar` method as an object with the keys you want to override.
For example, we could have a bar chart without a stroke on each bar by doing the following:
```javascript
new Chart(ctx).Bar({
data: data,
new Chart(ctx,{
type:"bar",
data: data,
options: {
barShowStroke: false
scales: {
xAxes: [{
stacked: true,
}],
yAxes: [{
stacked: true
}]
}
}
}
});
// This will create a chart with all of the default options, merged from the global config,
// and the Bar chart defaults but this particular instance will have `barShowStroke` set to false.
// and the Bar chart defaults but this particular instance will have `stacked` set to true
// for both x and y axes.
```
We can also change these defaults values for each Bar type that is created, this object is available at `Chart.defaults.Bar`.
#### barPercentage vs categoryPercentage
The following shows the relationship between the bar percentage option and the category percentage option.
```text
// categoryPercentage: 1.0
// barPercentage: 1.0
Bar: | 1.0 | 1.0 |
Category: | 1.0 |
Sample: |===========|
// categoryPercentage: 1.0
// barPercentage: 0.5
Bar: |.5| |.5|
Category: | 1.0 |
Sample: |==============|
// categoryPercentage: 0.5
// barPercentage: 1.0
Bar: |1.||1.|
Category: | .5 |
Sample: |==============|
```
### Prototype methods
#### .getBarsAtEvent( event )
#### .getElementsAtEvent( event )
Calling `getBarsAtEvent(event)` on your Chart instance passing an argument of an event, or jQuery event, will return the bar elements that are at that the same position of that event.
Calling `getElementsAtEvent(event)` on your Chart instance passing an argument of an event, or jQuery event, will return the point elements that are at that the same position of that event.
```javascript
canvas.onclick = function(evt){
var activeBars = myBarChart.getBarsAtEvent(evt);
// => activeBars is an array of bars on the canvas that are at the same position as the click event.
var activePoints = myLineChart.getElementsAtEvent(evt);
// => activePoints is an array of points on the canvas that are at the same position as the click event.
};
```
This functionality may be useful for implementing DOM based tooltips, or triggering custom behaviour in your application.
#### .getElementAtEvent( event )
Calling `getElementAtEvent(event)` on your Chart instance passing an argument of an event, or jQuery event, will return the single element at the event position. If there are multiple items within range, only the first is returned
#### .update( )
Calling `update()` on your Chart instance will re-render the chart with any updated values, allowing you to edit the value of multiple existing points, then render those in one animated render loop.
```javascript
myBarChart.datasets[0].bars[2].value = 50;
myBarChart.data.datasets[0].data[2] = 50;
// Would update the first dataset's value of 'March' to be 50
myBarChart.update();
// Calling update now animates the position of March from 90 to 50.
```
#### .addData( valuesArray, label )
Calling `addData(valuesArray, label)` on your Chart instance passing an array of values for each dataset, along with a label for those bars.
```javascript
// The values array passed into addData should be one for each dataset in the chart
myBarChart.addData([40, 60], "August");
// The new data will now animate at the end of the chart.
```
#### .removeData( )
Calling `removeData()` on your Chart instance will remove the first value for all datasets on the chart.
```javascript
myBarChart.removeData();
// The chart will now animate and remove the first bar
```
```
+38 -76
Ver Arquivo
@@ -15,7 +15,11 @@ They are often useful for comparing the points of two or more different data set
###Example usage
```javascript
var myRadarChart = new Chart(ctx).Radar(data, options);
var myRadarChart = new Chart(ctx,{
type:'radar',
data: data,
options: options
});
```
###Data structure
@@ -25,22 +29,22 @@ var data = {
datasets: [
{
label: "My First dataset",
fillColor: "rgba(220,220,220,0.2)",
strokeColor: "rgba(220,220,220,1)",
pointColor: "rgba(220,220,220,1)",
pointStrokeColor: "#fff",
pointHighlightFill: "#fff",
pointHighlightStroke: "rgba(220,220,220,1)",
backgroundColor: "rgba(220,220,220,0.2)",
borderColor: "rgba(220,220,220,1)",
pointBackgroundColor: "rgba(220,220,220,1)",
pointBorderColor: "#fff",
pointHoverBackgroundColor: "#fff",
pointHoverBorderColor: "rgba(220,220,220,1)",
data: [65, 59, 90, 81, 56, 55, 40]
},
{
label: "My Second dataset",
fillColor: "rgba(151,187,205,0.2)",
strokeColor: "rgba(151,187,205,1)",
pointColor: "rgba(151,187,205,1)",
pointStrokeColor: "#fff",
pointHighlightFill: "#fff",
pointHighlightStroke: "rgba(151,187,205,1)",
backgroundColor: "rgba(151,187,205,0.2)",
borderColor: "rgba(151,187,205,1)",
pointBackgroundColor: "rgba(151,187,205,1)",
pointBorderColor: "#fff",
pointHoverBackgroundColor: "#fff",
pointHoverBorderColor: "rgba(151,187,205,1)",
data: [28, 48, 40, 19, 96, 27, 100]
}
]
@@ -55,77 +59,35 @@ The label key on each dataset is optional, and can be used when generating a sca
These are the customisation options specific to Radar charts. These options are merged with the [global chart configuration options](#getting-started-global-chart-configuration), and form the options of the chart.
The default options for radar chart are defined in `Chart.defaults.radar`.
```javascript
{
//Boolean - Whether to show lines for each scale point
scaleShowLine : true,
//Boolean - Whether we show the angle lines out of the radar
angleShowLineOut : true,
//Boolean - Whether to show labels on the scale
scaleShowLabels : false,
// Boolean - Whether the scale should begin at zero
scaleBeginAtZero : true,
//String - Colour of the angle line
angleLineColor : "rgba(0,0,0,.1)",
//Number - Pixel width of the angle line
angleLineWidth : 1,
//String - Point label font declaration
pointLabelFontFamily : "'Arial'",
//String - Point label font weight
pointLabelFontStyle : "normal",
//Number - Point label font size in pixels
pointLabelFontSize : 10,
//String - Point label font colour
pointLabelFontColor : "#666",
//Boolean - Whether to show a dot for each point
pointDot : true,
//Number - Radius of each point dot in pixels
pointDotRadius : 3,
//Number - Pixel width of point dot stroke
pointDotStrokeWidth : 1,
//Number - amount extra to add to the radius to cater for hit detection outside the drawn point
pointHitDetectionRadius : 20,
//Boolean - Whether to show a stroke for datasets
datasetStroke : true,
//Number - Pixel width of dataset stroke
datasetStrokeWidth : 2,
//Boolean - Whether to fill the dataset with a colour
datasetFill : true,
{% raw %}
//String - A legend template
legendTemplate : "<ul class=\"<%=name.toLowerCase()%>-legend\"><% for (var i=0; i<datasets.length; i++){%><li><span style=\"background-color:<%=datasets[i].strokeColor%>\"></span><%if(datasets[i].label){%><%=datasets[i].label%><%}%></li><%}%></ul>"
{% endraw %}
}
```
Name | Type | Default | Description
--- | --- | --- | ---
scale | Array | [See Scales](#scales) and [Defaults for Radial Linear Scale](#scales-radial-linear-scale) | Options for the one scale used on the chart. Use this to style the ticks, labels, and grid lines.
*scale*.type | String |"radialLinear" | As defined in ["Radial Linear"](#scales-radial-linear-scale).
*elements*.line | Array | | Options for all line elements used on the chart, as defined in the global elements, duplicated here to show Radar chart specific defaults.
*elements.line*.tension | Number | 0 | Tension exhibited by lines when calculating splineCurve.
You can override these for your `Chart` instance by passing a second argument into the `Radar` method as an object with the keys you want to override.
For example, we could have a radar chart without a point for each on piece of data by doing the following:
```javascript
new Chart(ctx).Radar(data, {
pointDot: false
new Chart(ctx, {
type:"radar",
data: data,
options: {
scale: {
reverse: true,
ticks: {
beginAtZero: true
}
}
}
});
// This will create a chart with all of the default options, merged from the global config,
// and the Bar chart defaults but this particular instance will have `pointDot` set to false.
// and the Radar chart defaults but this particular instance's scale will be reversed as
// well as the ticks beginning at zero.
```
We can also change these defaults values for each Radar type that is created, this object is available at `Chart.defaults.Radar`.
@@ -174,4 +136,4 @@ Calling `removeData()` on your Chart instance will remove the first value for al
```javascript
myRadarChart.removeData();
// Other points will now animate to their correct positions.
```
```
+7 -46
Ver Arquivo
@@ -60,52 +60,13 @@ As you can see, for the chart data you pass in an array of objects, with a value
These are the customisation options specific to Polar Area charts. These options are merged with the [global chart configuration options](#getting-started-global-chart-configuration), and form the options of the chart.
```javascript
{
//Boolean - Show a backdrop to the scale label
scaleShowLabelBackdrop : true,
//String - The colour of the label backdrop
scaleBackdropColor : "rgba(255,255,255,0.75)",
// Boolean - Whether the scale should begin at zero
scaleBeginAtZero : true,
//Number - The backdrop padding above & below the label in pixels
scaleBackdropPaddingY : 2,
//Number - The backdrop padding to the side of the label in pixels
scaleBackdropPaddingX : 2,
//Boolean - Show line for each value in the scale
scaleShowLine : true,
//Boolean - Stroke a line around each segment in the chart
segmentShowStroke : true,
//String - The colour of the stroke on each segment.
segmentStrokeColor : "#fff",
//Number - The width of the stroke value in pixels
segmentStrokeWidth : 2,
//Number - Amount of animation steps
animationSteps : 100,
//String - Animation easing effect.
animationEasing : "easeOutBounce",
//Boolean - Whether to animate the rotation of the chart
animateRotate : true,
//Boolean - Whether to animate scaling the chart from the centre
animateScale : false,
{% raw %}
//String - A legend template
legendTemplate : "<ul class=\"<%=name.toLowerCase()%>-legend\"><% for (var i=0; i<segments.length; i++){%><li><span style=\"background-color:<%=segments[i].fillColor%>\"></span><%if(segments[i].label){%><%=segments[i].label%><%}%></li><%}%></ul>"
{% endraw %}
}
```
Name | Type | Default | Description
--- | --- | --- | ---
scale | Array | [See Scales](#scales) and [Defaults for Radial Linear Scale](#getting-started-radial-linear-scale) | Options for the one scale used on the chart. Use this to style the ticks, labels, and grid.
*scale*.type | String |"radialLinear" | As defined in ["Radial Linear"](#scales-radial-linear-scale).
*scale*.lineArc | Boolean | true | When true, lines are circular.
*animation*.animateRotate | Boolean |true | If true, will animate the rotation of the chart.
*animation*.animateScale | Boolean | true | If true, will animate scaling the chart.
You can override these for your `Chart` instance by passing a second argument into the `PolarArea` method as an object with the keys you want to override.
+44 -54
Ver Arquivo
@@ -24,35 +24,44 @@ They are also registered under two aliases in the `Chart` core. Other than their
```javascript
// For a pie chart
var myPieChart = new Chart(ctx[0]).Pie(data,options);
var myPieChart = new Chart(ctx[0],{
type:'pie',
data: data,
options: options
});
// And for a doughnut chart
var myDoughnutChart = new Chart(ctx[1]).Doughnut(data,options);
var myDoughnutChart = new Chart(ctx[1], {
type:'doughnut',
data: data,
options: options
});
```
### Data structure
```javascript
var data = [
{
value: 300,
color:"#F7464A",
highlight: "#FF5A5E",
label: "Red"
},
{
value: 50,
color: "#46BFBD",
highlight: "#5AD3D1",
label: "Green"
},
{
value: 100,
color: "#FDB45C",
highlight: "#FFC870",
label: "Yellow"
}
]
var data = {
labels: [
"Red",
"Green",
"Yellow"
],
datasets: [
{
data: [300, 50, 100],
backgroundColor: [
"#F7464A",
"#46BFBD",
"#FDB45C"
],
hoverBackgroundColor: [
"#FF5A5E",
"#5AD3D1",
"#FFC870"
]
}]
};
```
For a pie chart, you must pass in an array of objects with a value and an optional color property. The value attribute should be a number, Chart.js will total all of the numbers and calculate the relative proportion of each. The color attribute should be a string. Similar to CSS, for this string you can use HEX notation, RGB, RGBA or HSL.
@@ -61,44 +70,25 @@ For a pie chart, you must pass in an array of objects with a value and an option
These are the customisation options specific to Pie & Doughnut charts. These options are merged with the [global chart configuration options](#getting-started-global-chart-configuration), and form the options of the chart.
```javascript
{
//Boolean - Whether we should show a stroke on each segment
segmentShowStroke : true,
Name | Type | Default | Description
--- | --- | --- | ---
cutoutPercentage | Number | 50 - for doughnut, 0 - for pie | The percentage of the chart that is cut out of the middle.
scale | Array | [See Scales](#scales) and [Defaults for Radial Linear Scale](#getting-started-radial-linear-scale) | Options for the one scale used on the chart. Use this to style the ticks, labels, and grid.
*scale*.type | String |"radialLinear" | As defined in ["Radial Linear"](#scales-radial-linear-scale).
*scale*.lineArc | Boolean | true | When true, lines are arced compared to straight when false.
*animation*.animateRotate | Boolean |true | If true, will animate the rotation of the chart.
*animation*.animateScale | Boolean | false | If true, will animate scaling the Doughnut from the centre.
//String - The colour of each segment stroke
segmentStrokeColor : "#fff",
//Number - The width of each segment stroke
segmentStrokeWidth : 2,
//Number - The percentage of the chart that we cut out of the middle
percentageInnerCutout : 50, // This is 0 for Pie charts
//Number - Amount of animation steps
animationSteps : 100,
//String - Animation easing effect
animationEasing : "easeOutBounce",
//Boolean - Whether we animate the rotation of the Doughnut
animateRotate : true,
//Boolean - Whether we animate scaling the Doughnut from the centre
animateScale : false,
{% raw %}
//String - A legend template
legendTemplate : "<ul class=\"<%=name.toLowerCase()%>-legend\"><% for (var i=0; i<segments.length; i++){%><li><span style=\"background-color:<%=segments[i].fillColor%>\"></span><%if(segments[i].label){%><%=segments[i].label%><%}%></li><%}%></ul>"
{% endraw %}
}
```
You can override these for your `Chart` instance by passing a second argument into the `Doughnut` method as an object with the keys you want to override.
For example, we could have a doughnut chart that animates by scaling out from the centre like so:
```javascript
new Chart(ctx).Doughnut(data, {
animateScale: true
new Chart(ctx,{
type:"doughnut",
animation:{
animateScale:true
}
});
// This will create a chart with all of the default options, merged from the global config,
// and the Doughnut chart defaults but this particular instance will have `animateScale` set to `true`.
-1
Ver Arquivo
@@ -27,7 +27,6 @@ var srcFiles = [
'./node_modules/color/dist/color.min.js',
'./src/core/core.js',
'./src/core/core.helpers.js',
'./src/core/core.chart.js',
'./src/core/core.element.js',
'./src/core/**',
'./src/controllers/**',
+14 -2
Ver Arquivo
@@ -1,7 +1,19 @@
module.exports = function(config) {
config.set({
var configuration = {
browsers: ['Firefox'],
customLaunchers: {
Chrome_travis_ci: {
base: 'Chrome',
flags: ['--no-sandbox']
}
},
frameworks: ['jasmine'],
reporters: ['progress', 'html'],
});
};
if (process.env.TRAVIS) {
configuration.browsers.push('Chrome_travis_ci');
}
config.set(configuration);
};
+3
Ver Arquivo
@@ -43,6 +43,9 @@
type: 'bar',
data: barChartData,
options: {
tooltips: {
mode: 'label'
},
responsive: true,
scales: {
xAxes: [{
+2 -2
Ver Arquivo
@@ -18,8 +18,8 @@
</head>
<body>
<div id="canvas-holder" style="width:50%">
<canvas id="chart-area" width="500" height="500" />
<div id="canvas-holder" style="width:100%">
<canvas id="chart-area" />
</div>
<button id="randomizeData">Randomize Data</button>
<button id="addDataset">Add Dataset</button>
+110 -116
Ver Arquivo
@@ -2,149 +2,143 @@
<html>
<head>
<title>Line Chart with Custom Tooltips</title>
<script src="../Chart.js"></script>
<script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
<style>
<title>Line Chart with Custom Tooltips</title>
<script src="../Chart.js"></script>
<script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
<style>
#canvas-holder1 {
width: 300px;
margin: 20px auto;
width: 300px;
margin: 20px auto;
}
#canvas-holder2 {
width: 50%;
margin: 20px 25%;
width: 50%;
margin: 20px 25%;
}
#chartjs-tooltip {
opacity: 1;
position: absolute;
background: rgba(0, 0, 0, .7);
color: white;
border-radius: 3px;
-webkit-transition: all .1s ease;
transition: all .1s ease;
pointer-events: none;
-webkit-transform: translate(-50%, 0);
transform: translate(-50%, 0);
opacity: 1;
position: absolute;
background: rgba(0, 0, 0, .7);
color: white;
border-radius: 3px;
-webkit-transition: all .1s ease;
transition: all .1s ease;
pointer-events: none;
-webkit-transform: translate(-50%, 0);
transform: translate(-50%, 0);
}
.chartjs-tooltip-key {
display: inline-block;
width: 10px;
height: 10px;
display: inline-block;
width: 10px;
height: 10px;
}
</style>
</style>
</head>
<body>
<div id="canvas-holder1">
<canvas id="chart1" width="300" height="30" />
</div>
<script>
<div id="canvas-holder1">
<canvas id="chart1" width="300" height="100" />
</div>
<script>
window.count = 0;
Chart.defaults.global.pointHitDetectionRadius = 1;
var customTooltips = function(tooltip) {
console.log(tooltip._view);
console.log(window.count++, tooltip);
// Tooltip Element
var tooltipEl = $('#chartjs-tooltip');
// Tooltip Element
var tooltipEl = $('#chartjs-tooltip');
if (!tooltipEl[0]) {
$('body').append('<div id="chartjs-tooltip"></div>');
tooltipEl = $('#chartjs-tooltip');
}
if (!tooltipEl[0]) {
$('body').append('<div id="chartjs-tooltip"></div>');
tooltipEl = $('#chartjs-tooltip');
}
// Hide if no tooltip
if (!tooltip._view.opacity) {
tooltipEl.css({
opacity: 0
});
$('.chartjs-wrap canvas')
.each(function(index, el) {
$(el).css('cursor', 'default');
});
return;
}
$(tooltip._chart.canvas).css('cursor', 'pointer');
// Set caret Position
tooltipEl.removeClass('above below no-transform');
if (tooltip._view.yAlign) {
tooltipEl.addClass(tooltip._view.yAlign);
} else {
tooltipEl.addClass('no-transform');
}
// Set Text
if (tooltip._view.text) {
tooltipEl.html(tooltip._view.text);
} else if (tooltip._view.labels) {
var innerHtml = '<div class="title">' + tooltip._view.title + '</div>';
for (var i = 0; i < tooltip._view.labels.length; i++) {
innerHtml += [
'<div class="section">',
' <span class="key" style="background-color:' + tooltip._view.legendColors[i].fill + '"></span>',
' <span class="value">' + tooltip._view.labels[i] + '</span>',
'</div>'
].join('');
}
tooltipEl.html(innerHtml);
}
// Find Y Location on page
var top = 0;
if (tooltip._view.yAlign) {
if (tooltip._view.yAlign == 'above') {
top = tooltip._view.y - tooltip._view.caretHeight - tooltip._view.caretPadding;
} else {
top = tooltip._view.y + tooltip._view.caretHeight + tooltip._view.caretPadding;
}
}
var offset = $(tooltip._chart.canvas).offset();
// Display, position, and set styles for font
// Hide if no tooltip
if (!tooltip.opacity) {
tooltipEl.css({
opacity: 1,
width: tooltip._view.width ? (tooltip._view.width + 'px') : 'auto',
left: offset.left + tooltip._view.x + 'px',
top: offset.top + top + 'px',
fontFamily: tooltip._view._fontFamily,
fontSize: tooltip._view.fontSize,
fontStyle: tooltip._view._fontStyle,
padding: tooltip._view.yPadding + 'px ' + tooltip._view.xPadding + 'px',
opacity: 0
});
$('.chartjs-wrap canvas')
.each(function(index, el) {
$(el).css('cursor', 'default');
});
return;
}
$(this._chart.canvas).css('cursor', 'pointer');
// Set caret Position
tooltipEl.removeClass('above below no-transform');
if (tooltip.yAlign) {
tooltipEl.addClass(tooltip.yAlign);
} else {
tooltipEl.addClass('no-transform');
}
// Set Text
if (tooltip.body) {
var innerHtml = [
(tooltip.beforeTitle || []).join('\n'), (tooltip.title || []).join('\n'), (tooltip.afterTitle || []).join('\n'), (tooltip.beforeBody || []).join('\n'), (tooltip.body || []).join('\n'), (tooltip.afterBody || []).join('\n'), (tooltip.beforeFooter || [])
.join('\n'), (tooltip.footer || []).join('\n'), (tooltip.afterFooter || []).join('\n')
];
tooltipEl.html(innerHtml.join('\n'));
}
// Find Y Location on page
var top = 0;
if (tooltip.yAlign) {
if (tooltip.yAlign == 'above') {
top = tooltip.y - tooltip.caretHeight - tooltip.caretPadding;
} else {
top = tooltip.y + tooltip.caretHeight + tooltip.caretPadding;
}
}
var offset = $(this._chart.canvas).offset();
// Display, position, and set styles for font
tooltipEl.css({
opacity: 1,
width: tooltip.width ? (tooltip.width + 'px') : 'auto',
left: offset.left + tooltip.x + 'px',
top: offset.top + top + 'px',
fontFamily: tooltip._fontFamily,
fontSize: tooltip.fontSize,
fontStyle: tooltip._fontStyle,
padding: tooltip.yPadding + 'px ' + tooltip.xPadding + 'px',
});
};
var randomScalingFactor = function() {
return Math.round(Math.random() * 100);
return Math.round(Math.random() * 100);
};
var lineChartData = {
labels: ["January", "February", "March", "April", "May", "June", "July"],
datasets: [{
label: "My First dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
}, {
label: "My Second dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
}]
labels: ["January", "February", "March", "April", "May", "June", "July"],
datasets: [{
label: "My First dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
}, {
label: "My Second dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
}]
};
window.onload = function() {
var chartEl = document.getElementById("chart1");
window.myLine = new Chart(chartEl, {
type: 'line',
data: lineChartData,
options: {
tooltips: {
enabled: false,
custom: customTooltips
}
}
});
var chartEl = document.getElementById("chart1");
window.myLine = new Chart(chartEl, {
type: 'line',
data: lineChartData,
options: {
tooltips: {
enabled: false,
custom: customTooltips
}
}
});
};
</script>
</script>
</body>
</html>
+2 -2
Ver Arquivo
@@ -60,7 +60,7 @@
xAxes: [{
display: true,
scaleLabel: {
show: true,
display: true,
labelString: 'x axis'
}
}],
@@ -68,7 +68,7 @@
display: true,
type: 'logarithmic',
scaleLabel: {
show: true,
display: true,
labelString: 'y axis'
}
}]
+175
Ver Arquivo
@@ -0,0 +1,175 @@
<!doctype html>
<html>
<head>
<title>Line Chart</title>
<script src="../Chart.js"></script>
<script src="../node_modules/jquery/dist/jquery.min.js"></script>
<style>
canvas {
-webkit-box-shadow: 0 0 20px 0 rgba(0, 0, 0, .5);
}
</style>
</head>
<body>
<div style="width:100%;">
<canvas id="canvas" style="width:100%;height:100%"></canvas>
</div>
<br>
<br>
<button id="randomizeData">Randomize Data</button>
<button id="addDataset">Add Dataset</button>
<button id="removeDataset">Remove Dataset</button>
<button id="addData">Add Data</button>
<button id="removeData">Remove Data</button>
<div>
<h3>Legend</h3>
<div id="legendContainer">
</div>
</div>
<script>
var randomScalingFactor = function() {
return Math.round(Math.random() * 100);
//return 0;
};
var randomColorFactor = function() {
return Math.round(Math.random() * 255);
};
var randomColor = function(opacity) {
return 'rgba(' + randomColorFactor() + ',' + randomColorFactor() + ',' + randomColorFactor() + ',' + (opacity || '.3') + ')';
};
var config = {
type: 'line',
data: {
labels: ["January", "February", "March", "April", "May", "June", "July"],
datasets: [{
label: "My First dataset",
// Skip a point in the middle
data: [randomScalingFactor(), randomScalingFactor(), NaN, randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()],
fill: true,
borderDash: [5, 5],
}, {
label: "My Second dataset",
// Skip first and last points
data: [NaN, randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), NaN],
}]
},
options: {
responsive: true,
tooltips: {
mode: 'label',
},
hover: {
mode: 'label'
},
scales: {
xAxes: [{
display: true,
scaleLabel: {
display: true,
labelString: 'Month'
}
}],
yAxes: [{
display: true,
scaleLabel: {
display: true,
labelString: 'Value'
},
}]
}
}
};
$.each(config.data.datasets, function(i, dataset) {
dataset.borderColor = randomColor(0.4);
dataset.backgroundColor = randomColor(0.5);
dataset.pointBorderColor = randomColor(0.7);
dataset.pointBackgroundColor = randomColor(0.5);
dataset.pointBorderWidth = 1;
});
console.log(config.data);
window.onload = function() {
var ctx = document.getElementById("canvas").getContext("2d");
window.myLine = new Chart(ctx, config);
updateLegend();
};
function updateLegend() {
$legendContainer = $('#legendContainer');
$legendContainer.empty();
$legendContainer.append(window.myLine.generateLegend());
}
$('#randomizeData').click(function() {
$.each(config.data.datasets, function(i, dataset) {
dataset.data = dataset.data.map(function() {
return randomScalingFactor();
});
});
window.myLine.update();
updateLegend();
});
$('#addDataset').click(function() {
var newDataset = {
label: 'Dataset ' + config.data.datasets.length,
borderColor: randomColor(0.4),
backgroundColor: randomColor(0.5),
pointBorderColor: randomColor(0.7),
pointBackgroundColor: randomColor(0.5),
pointBorderWidth: 1,
data: [],
};
for (var index = 0; index < config.data.labels.length; ++index) {
newDataset.data.push(randomScalingFactor());
}
config.data.datasets.push(newDataset);
window.myLine.update();
updateLegend();
});
$('#addData').click(function() {
if (config.data.datasets.length > 0) {
config.data.labels.push('dataset #' + config.data.labels.length);
$.each(config.data.datasets, function(i, dataset) {
dataset.data.push(randomScalingFactor());
});
window.myLine.update();
updateLegend();
}
});
$('#removeDataset').click(function() {
config.data.datasets.splice(0, 1);
window.myLine.update();
updateLegend();
});
$('#removeData').click(function() {
config.data.labels.splice(-1, 1); // remove the label first
config.data.datasets.forEach(function(dataset, datasetIndex) {
dataset.data.pop();
});
window.myLine.update();
updateLegend();
});
</script>
</body>
</html>
+174
Ver Arquivo
@@ -0,0 +1,174 @@
<!doctype html>
<html>
<head>
<title>Line Chart</title>
<script src="../Chart.js"></script>
<script src="../node_modules/jquery/dist/jquery.min.js"></script>
<style>
canvas {
-webkit-box-shadow: 0 0 20px 0 rgba(0, 0, 0, .5);
}
</style>
</head>
<body>
<div style="width:100%;">
<canvas id="canvas" style="width:100%;height:100%"></canvas>
</div>
<br>
<br>
<button id="randomizeData">Randomize Data</button>
<button id="addDataset">Add Dataset</button>
<button id="removeDataset">Remove Dataset</button>
<button id="addData">Add Data</button>
<button id="removeData">Remove Data</button>
<div>
<h3>Legend</h3>
<div id="legendContainer">
</div>
</div>
<script>
var randomScalingFactor = function() {
return Math.round(Math.random() * 100 * (Math.random() > 0.5 ? -1 : 1));
};
var randomColorFactor = function() {
return Math.round(Math.random() * 255);
};
var randomColor = function(opacity) {
return 'rgba(' + randomColorFactor() + ',' + randomColorFactor() + ',' + randomColorFactor() + ',' + (opacity || '1') + ')';
};
var config = {
type: 'line',
data: {
labels: ["January", "February", "March", "April", "May", "June", "July"],
datasets: [{
label: "My First dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()],
}, {
label: "My Second dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()],
}, {
label: "My Third dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()],
}, {
label: "My Third dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()],
}]
},
options: {
responsive: true,
tooltips: {
mode: 'label',
},
hover: {
mode: 'label'
},
scales: {
xAxes: [{
scaleLabel: {
display: true,
labelString: 'Month'
}
}],
yAxes: [{
stacked: true,
scaleLabel: {
display: true,
labelString: 'Value'
}
}]
}
}
};
$.each(config.data.datasets, function(i, dataset) {
var color = randomColor(1);
dataset.borderColor = color;
dataset.backgroundColor = color;
dataset.pointBorderColor = color;
dataset.pointBackgroundColor = color;
dataset.pointBorderWidth = 1;
});
console.log(config.data);
window.onload = function() {
var ctx = document.getElementById("canvas").getContext("2d");
window.myLine = new Chart(ctx, config);
updateLegend();
};
function updateLegend() {
$legendContainer = $('#legendContainer');
$legendContainer.empty();
$legendContainer.append(window.myLine.generateLegend());
}
$('#randomizeData').click(function() {
$.each(config.data.datasets, function(i, dataset) {
dataset.data = dataset.data.map(function() {
return randomScalingFactor();
});
});
window.myLine.update();
updateLegend();
});
$('#addDataset').click(function() {
var newDataset = {
label: 'Dataset ' + config.data.datasets.length,
borderColor: randomColor(0.4),
backgroundColor: randomColor(0.5),
pointBorderColor: randomColor(0.7),
pointBackgroundColor: randomColor(0.5),
pointBorderWidth: 1,
data: [],
};
for (var index = 0; index < config.data.labels.length; ++index) {
newDataset.data.push(randomScalingFactor());
}
config.data.datasets.push(newDataset);
window.myLine.update();
updateLegend();
});
$('#addData').click(function() {
if (config.data.datasets.length > 0) {
config.data.labels.push('dataset #' + config.data.labels.length);
$.each(config.data.datasets, function(i, dataset) {
dataset.data.push(randomScalingFactor());
});
window.myLine.update();
updateLegend();
}
});
$('#removeDataset').click(function() {
config.data.datasets.splice(0, 1);
window.myLine.update();
updateLegend();
});
$('#removeData').click(function() {
config.data.labels.splice(-1, 1); // remove the label first
config.data.datasets.forEach(function(dataset, datasetIndex) {
dataset.data.pop();
});
window.myLine.update();
updateLegend();
});
</script>
</body>
</html>
+2 -2
Ver Arquivo
@@ -77,14 +77,14 @@
// round: 'day'
},
scaleLabel: {
show: true,
display: true,
labelString: 'Date'
}
}, ],
yAxes: [{
display: true,
scaleLabel: {
show: true,
display: true,
labelString: 'value'
}
}]
+2 -2
Ver Arquivo
@@ -92,14 +92,14 @@
// round: 'day'
},
scaleLabel: {
show: true,
display: true,
labelString: 'Date'
}
}, ],
yAxes: [{
display: true,
scaleLabel: {
show: true,
display: true,
labelString: 'value'
}
}]
+33 -1
Ver Arquivo
@@ -19,6 +19,7 @@
<br>
<br>
<button id="randomizeData">Randomize Data</button>
<button id="changeDataObject">Change Data Object</button>
<button id="addDataset">Add Dataset</button>
<button id="removeDataset">Remove Dataset</button>
<button id="addData">Add Data</button>
@@ -30,7 +31,8 @@
</div>
<script>
var randomScalingFactor = function() {
return Math.round(Math.random() * 100 * (Math.random() > 0.5 ? -1 : 1));
return Math.round(Math.random() * 100);
//return 0;
};
var randomColorFactor = function() {
return Math.round(Math.random() * 255);
@@ -101,6 +103,10 @@
scaleLabel: {
show: true,
labelString: 'Value'
},
ticks: {
suggestedMin: -10,
suggestedMax: 250,
}
}]
}
@@ -142,6 +148,32 @@
updateLegend();
});
$('#changeDataObject').click(function() {
config.data = {
labels: ["July", "August", "September", "October", "November", "December"],
datasets: [{
label: "My First dataset",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()],
fill: false,
}, {
label: "My Second dataset",
fill: false,
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()],
}]
};
$.each(config.data.datasets, function(i, dataset) {
dataset.borderColor = randomColor(0.4);
dataset.backgroundColor = randomColor(0.5);
dataset.pointBorderColor = randomColor(0.7);
dataset.pointBackgroundColor = randomColor(0.5);
dataset.pointBorderWidth = 1;
});
// Update the chart
window.myLine.update();
});
$('#addDataset').click(function() {
var newDataset = {
label: 'Dataset ' + config.data.datasets.length,
+8 -5
Ver Arquivo
@@ -8,7 +8,7 @@
</head>
<body>
<div id="canvas-holder" style="width:50%" width="50%">
<div id="canvas-holder" style="width:100%">
<canvas id="chart-area"></canvas>
</div>
<button id="randomizeData">Randomize Data</button>
@@ -17,7 +17,7 @@
<div>
<h3>Legend</h3>
<div id="legendContainer">
</div>
</div>
<script>
@@ -60,9 +60,12 @@
options: {
responsive: true,
scale: {
beginAtZero: true,
reverse: false
}
ticks: {
beginAtZero: true
},
reverse: false
},
animateRotate:false
}
};
+152
Ver Arquivo
@@ -0,0 +1,152 @@
<!doctype html>
<html>
<head>
<title>Radar Chart</title>
<script src="../Chart.js"></script>
<script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
</head>
<body>
<div style="width:50%">
<canvas id="canvas" height="450" width="450"></canvas>
</div>
<button id="randomizeData">Randomize Data</button>
<button id="addDataset">Add Dataset</button>
<button id="removeDataset">Remove Dataset</button>
<button id="addData">Add Data</button>
<button id="removeData">Remove Data</button>
<div>
<h3>Legend</h3>
<div id="legendContainer">
</div>
</div>
<script>
var randomScalingFactor = function() {
return Math.round(Math.random() * 100);
};
var randomColorFactor = function() {
return Math.round(Math.random() * 255);
};
var randomColor = function(opacity) {
return 'rgba(' + randomColorFactor() + ',' + randomColorFactor() + ',' + randomColorFactor() + ',' + (opacity || '.3') + ')';
};
var config = {
type: 'radar',
data: {
labels: ["Eating", "Drinking", "Sleeping", "Designing", "Coding", "Cycling", "Running"],
datasets: [{
label: "Skip first dataset",
borderColor: 'rgb(255, 0, 0)',
backgroundColor: "rgba(255,255,0,0.5)",
pointBackgroundColor: "rgba(220,220,220,1)",
data: [NaN, randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
}, {
label: "Skip mid dataset",
borderColor: 'rgb(255, 0, 255)',
backgroundColor: "rgba(0, 255, 0, 0.5)",
pointBackgroundColor: "rgba(151,187,205,1)",
hoverPointBackgroundColor: "#fff",
pointHighlightStroke: "rgba(151,187,205,1)",
data: [randomScalingFactor(), randomScalingFactor(), NaN, randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
},{
label: "Skip last dataset",
borderColor: 'rgb(0, 255, 255)',
backgroundColor: "rgba(0, 0, 255, 0.5)",
pointBackgroundColor: "rgba(151,187,205,1)",
hoverPointBackgroundColor: "#fff",
pointHighlightStroke: "rgba(151,187,205,1)",
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), NaN]
}]
},
options: {
elements: {
line: {
tension: 0.0,
}
},
scale: {
beginAtZero: true,
reverse: false
}
}
};
function updateLegend() {
$legendContainer = $('#legendContainer');
$legendContainer.empty();
$legendContainer.append(window.myRadar.generateLegend());
}
window.onload = function() {
window.myRadar = new Chart(document.getElementById("canvas"), config);
updateLegend();
};
$('#randomizeData').click(function() {
$.each(config.data.datasets, function(i, dataset) {
dataset.data = dataset.data.map(function() {
return randomScalingFactor();
});
});
window.myRadar.update();
updateLegend();
});
$('#addDataset').click(function() {
var newDataset = {
label: 'Dataset ' + config.data.datasets.length,
borderColor: randomColor(0.4),
backgroundColor: randomColor(0.5),
pointBorderColor: randomColor(0.7),
pointBackgroundColor: randomColor(0.5),
pointBorderWidth: 1,
data: [],
};
for (var index = 0; index < config.data.labels.length; ++index) {
newDataset.data.push(randomScalingFactor());
}
config.data.datasets.push(newDataset);
window.myRadar.update();
updateLegend();
});
$('#addData').click(function() {
if (config.data.datasets.length > 0) {
config.data.labels.push('dataset #' + config.data.labels.length);
$.each(config.data.datasets, function (i, dataset) {
dataset.data.push(randomScalingFactor());
});
window.myRadar.update();
updateLegend();
}
});
$('#removeDataset').click(function() {
config.data.datasets.splice(0, 1);
window.myRadar.update();
updateLegend();
});
$('#removeData').click(function() {
config.data.labels.pop(); // remove the label first
$.each(config.data.datasets, function(i, dataset) {
dataset.data.pop();
});
window.myRadar.update();
updateLegend();
});
</script>
</body>
</html>
+9 -7
Ver Arquivo
@@ -8,8 +8,8 @@
</head>
<body>
<div style="width:50%">
<canvas id="canvas" height="450" width="450"></canvas>
<div style="width:100%">
<canvas id="canvas"></canvas>
</div>
<button id="randomizeData">Randomize Data</button>
<button id="addDataset">Add Dataset</button>
@@ -19,7 +19,7 @@
<div>
<h3>Legend</h3>
<div id="legendContainer">
</div>
</div>
<script>
@@ -41,7 +41,7 @@
label: "My First dataset",
backgroundColor: "rgba(220,220,220,0.2)",
pointBackgroundColor: "rgba(220,220,220,1)",
data: [null, randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
}, {
label: 'Hidden dataset',
hidden: true,
@@ -52,13 +52,15 @@
pointBackgroundColor: "rgba(151,187,205,1)",
hoverPointBackgroundColor: "#fff",
pointHighlightStroke: "rgba(151,187,205,1)",
data: [null, randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
data: [randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor(), randomScalingFactor()]
},]
},
options: {
scale: {
beginAtZero: true,
reverse: false
reverse: true,
ticks: {
beginAtZero: true
}
}
}
};
+2 -2
Ver Arquivo
@@ -149,7 +149,7 @@
},
scaleLabel: {
labelString: 'Frequency',
show: true,
display: true,
}
}],
yAxes: [{
@@ -161,7 +161,7 @@
},
scaleLabel: {
labelString: 'Voltage',
show: true
display: true
}
}]
}
+2 -2
Ver Arquivo
@@ -96,7 +96,7 @@
zeroLineColor: "rgba(0,255,0,1)"
},
scaleLabel: {
show: true,
display: true,
labelString: 'x axis'
}
}],
@@ -106,7 +106,7 @@
zeroLineColor: "rgba(0,255,0,1)"
},
scaleLabel: {
show: true,
display: true,
labelString: 'y axis'
}
}]
+12 -3
Ver Arquivo
@@ -24,14 +24,23 @@
},
tooltips: {
template: "(<%= value.x %>, <%= value.y %>)",
multiTemplate: "<%if (datasetLabel){%><%=datasetLabel%>: <%}%>(<%= value.x %>, <%= value.y %>)",
callbacks: {
title: function(tooltipItems, data) {
// Title doesn't make sense for scatter since we format the data as a point
return '';
},
label: function(tooltipItem, data) {
return '(' + tooltipItem.xLabel + ', ' + tooltipItem.yLabel + ')';
}
}
},
};
// Register the default config for this type
Chart.defaults.bubble = defaultConfig;
Chart.Bubble = function(context, config) {
config.options = helpers.configMerge(defaultConfig, config.options);
config.type = 'bubble';
return new Chart(context, config);
};
+17 -1
Ver Arquivo
@@ -7,7 +7,23 @@
var defaultConfig = {
aspectRatio: 1,
legendTemplate: "<ul class=\"<%=name.toLowerCase()%>-legend\"><% for (var i = 0; i < data.datasets[0].data.length; i++){%><li><span style=\"background-color:<%=data.datasets[0].backgroundColor[i]%>\"><%if(data.labels && i < data.labels.length){%><%=data.labels[i]%><%}%></span></li><%}%></ul>",
legendCallback: function(chart) {
var text = [];
text.push('<ul class="' + chart.id + '-legend">');
if (chart.data.datasets.length) {
for (var i = 0; i < chart.data.datasets[0].data.length; ++i) {
text.push('<li><span style="background-color:' + chart.data.datasets[0].backgroundColor[i] + '">');
if (chart.data.labels[i]) {
text.push(chart.data.labels[i]);
}
text.push('</span></li>');
}
}
text.push('</ul>');
return text.join("");
}
};
Chart.Doughnut = function(context, config) {
+17 -1
Ver Arquivo
@@ -7,7 +7,23 @@
var defaultConfig = {
aspectRatio: 1,
legendTemplate: "<ul class=\"<%=name.toLowerCase()%>-legend\"><% for (var i = 0; i < data.datasets[0].data.length; i++){%><li><span style=\"background-color:<%=data.datasets[0].backgroundColor[i]%>\"><%if(data.labels && i < data.labels.length){%><%=data.labels[i]%><%}%></span></li><%}%></ul>",
legendCallback: function(chart) {
var text = [];
text.push('<ul class="' + chart.id + '-legend">');
if (chart.data.datasets.length) {
for (var i = 0; i < chart.data.datasets[0].data.length; ++i) {
text.push('<li><span style="background-color:' + chart.data.datasets[0].backgroundColor[i] + '">');
if (chart.data.labels[i]) {
text.push(chart.data.labels[i]);
}
text.push('</span></li>');
}
}
text.push('</ul>');
return text.join("");
}
};
Chart.PolarArea = function(context, config) {
+16 -5
Ver Arquivo
@@ -24,15 +24,26 @@
},
tooltips: {
template: "(<%= value.x %>, <%= value.y %>)",
multiTemplate: "<%if (datasetLabel){%><%=datasetLabel%>: <%}%>(<%= value.x %>, <%= value.y %>)",
callbacks: {
title: function(tooltipItems, data) {
// Title doesn't make sense for scatter since we format the data as a point
return '';
},
label: function(tooltipItem, data) {
return '(' + tooltipItem.xLabel + ', ' + tooltipItem.yLabel + ')';
}
}
},
};
// Register the default config for this type
Chart.defaults.scatter = defaultConfig;
// Scatter charts use line controllers
Chart.controllers.scatter = Chart.controllers.line;
Chart.Scatter = function(context, config) {
config.options = helpers.configMerge(defaultConfig, config.options);
config.type = 'line';
config.type = 'scatter';
return new Chart(context, config);
};
+1 -1
Ver Arquivo
@@ -293,7 +293,7 @@
var leftTick = xScale.getPixelForValue(null, index, barIndex, this.chart.isCombo);
leftTick -= this.chart.isCombo ? (ruler.tickWidth / 2) : 0;
if (yScale.options.stacked) {
if (xScale.options.stacked) {
return leftTick + (ruler.categoryWidth / 2) + ruler.categorySpacing;
}
+10
Ver Arquivo
@@ -18,6 +18,16 @@
},
//The percentage of the chart that we cut out of the middle.
cutoutPercentage: 50,
// Need to override these to give a nice default
tooltips: {
callbacks: {
title: function() { return '';},
label: function(tooltipItem, data) {
return data.labels[tooltipItem.index] + ': ' + data.datasets[tooltipItem.datasetIndex].data[tooltipItem.index];
}
}
}
};
Chart.defaults.pie = helpers.clone(Chart.defaults.doughnut);
+87 -27
Ver Arquivo
@@ -169,6 +169,49 @@
this.updateBezierControlPoints();
},
getPointBackgroundColor: function(point, index) {
var backgroundColor = this.chart.options.elements.point.backgroundColor;
var dataset = this.getDataset();
if (point.custom && point.custom.backgroundColor) {
backgroundColor = point.custom.backgroundColor;
} else if (dataset.pointBackgroundColor) {
backgroundColor = helpers.getValueAtIndexOrDefault(dataset.pointBackgroundColor, index, backgroundColor);
} else if (dataset.backgroundColor) {
backgroundColor = dataset.backgroundColor;
}
return backgroundColor;
},
getPointBorderColor: function(point, index) {
var borderColor = this.chart.options.elements.point.borderColor;
var dataset = this.getDataset();
if (point.custom && point.custom.borderColor) {
borderColor = point.custom.borderColor;
} else if (dataset.pointBorderColor) {
borderColor = helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderColor, index, borderColor);
} else if (dataset.borderColor) {
borderColor = dataset.borderColor;
}
return borderColor;
},
getPointBorderWidth: function(point, index) {
var borderWidth = this.chart.options.elements.point.borderWidth;
var dataset = this.getDataset();
if (point.custom && point.custom.borderWidth !== undefined) {
borderWidth = point.custom.borderWidth;
} else if (dataset.pointBorderWidth !== undefined) {
borderWidth = helpers.getValueAtIndexOrDefault(dataset.pointBorderWidth, index, borderWidth);
} else if (dataset.borderWidth !== undefined) {
borderWidth = dataset.borderWidth;
}
return borderWidth;
},
updateElement: function(point, index, reset) {
var yScale = this.getScaleForId(this.getDataset().yAxisID);
var xScale = this.getScaleForId(this.getDataset().xAxisID);
@@ -193,13 +236,13 @@
// Desired view properties
_model: {
x: xScale.getPixelForValue(this.getDataset().data[index], index, this.index, this.chart.isCombo),
y: reset ? scaleBase : yScale.getPixelForValue(this.getDataset().data[index], index, this.index),
y: reset ? scaleBase : this.calculatePointY(this.getDataset().data[index], index, this.index, this.chart.isCombo),
// Appearance
tension: point.custom && point.custom.tension ? point.custom.tension : (this.getDataset().tension || this.chart.options.elements.line.tension),
radius: point.custom && point.custom.radius ? point.custom.radius : helpers.getValueAtIndexOrDefault(this.getDataset().radius, index, this.chart.options.elements.point.radius),
backgroundColor: point.custom && point.custom.backgroundColor ? point.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBackgroundColor, index, this.chart.options.elements.point.backgroundColor),
borderColor: point.custom && point.custom.borderColor ? point.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderColor, index, this.chart.options.elements.point.borderColor),
borderWidth: point.custom && point.custom.borderWidth ? point.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderWidth, index, this.chart.options.elements.point.borderWidth),
backgroundColor: this.getPointBackgroundColor(point, index),
borderColor: this.getPointBorderColor(point, index),
borderWidth: this.getPointBorderWidth(point, index),
// Tooltip
hitRadius: point.custom && point.custom.hitRadius ? point.custom.hitRadius : helpers.getValueAtIndexOrDefault(this.getDataset().hitRadius, index, this.chart.options.elements.point.hitRadius),
},
@@ -208,6 +251,39 @@
point._model.skip = point.custom && point.custom.skip ? point.custom.skip : (isNaN(point._model.x) || isNaN(point._model.y));
},
calculatePointY: function(value, index, datasetIndex, isCombo) {
var xScale = this.getScaleForId(this.getDataset().xAxisID);
var yScale = this.getScaleForId(this.getDataset().yAxisID);
if (yScale.options.stacked) {
var sumPos = 0,
sumNeg = 0;
for (var i = this.chart.data.datasets.length - 1; i > datasetIndex; i--) {
var ds = this.chart.data.datasets[i];
if (helpers.isDatasetVisible(ds)) {
if (ds.data[index] < 0) {
sumNeg += ds.data[index] || 0;
} else {
sumPos += ds.data[index] || 0;
}
}
}
if (value < 0) {
return yScale.getPixelForValue(sumNeg + value);
} else {
return yScale.getPixelForValue(sumPos + value);
}
return yScale.getPixelForValue(value);
}
return yScale.getPixelForValue(value);
},
updateBezierControlPoints: function() {
// Update bezier control points
helpers.each(this.getDataset().metaData, function(point, index) {
@@ -218,28 +294,12 @@
point._model.tension
);
point._model.controlPointPreviousX = controlPoints.previous.x;
point._model.controlPointNextX = controlPoints.next.x;
// Prevent the bezier going outside of the bounds of the graph
point._model.controlPointPreviousX = Math.max(Math.min(controlPoints.previous.x, this.chart.chartArea.right), this.chart.chartArea.left);
point._model.controlPointPreviousY = Math.max(Math.min(controlPoints.previous.y, this.chart.chartArea.bottom), this.chart.chartArea.top);
// Cap outer bezier handles to the upper/lower scale bounds
if (controlPoints.next.y > this.chart.chartArea.bottom) {
point._model.controlPointNextY = this.chart.chartArea.bottom;
} else if (controlPoints.next.y < this.chart.chartArea.top) {
point._model.controlPointNextY = this.chart.chartArea.top;
} else {
point._model.controlPointNextY = controlPoints.next.y;
}
// Cap inner bezier handles to the upper/lower scale bounds
if (controlPoints.previous.y > this.chart.chartArea.bottom) {
point._model.controlPointPreviousY = this.chart.chartArea.bottom;
} else if (controlPoints.previous.y < this.chart.chartArea.top) {
point._model.controlPointPreviousY = this.chart.chartArea.top;
} else {
point._model.controlPointPreviousY = controlPoints.previous.y;
}
point._model.controlPointNextX = Math.max(Math.min(controlPoints.next.x, this.chart.chartArea.right), this.chart.chartArea.left);
point._model.controlPointNextY = Math.max(Math.min(controlPoints.next.y, this.chart.chartArea.bottom), this.chart.chartArea.top);
// Now pivot the point for animation
point.pivot();
@@ -279,9 +339,9 @@
var index = point._index;
point._model.radius = point.custom && point.custom.radius ? point.custom.radius : helpers.getValueAtIndexOrDefault(this.getDataset().radius, index, this.chart.options.elements.point.radius);
point._model.backgroundColor = point.custom && point.custom.backgroundColor ? point.custom.backgroundColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBackgroundColor, index, this.chart.options.elements.point.backgroundColor);
point._model.borderColor = point.custom && point.custom.borderColor ? point.custom.borderColor : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderColor, index, this.chart.options.elements.point.borderColor);
point._model.borderWidth = point.custom && point.custom.borderWidth ? point.custom.borderWidth : helpers.getValueAtIndexOrDefault(this.getDataset().pointBorderWidth, index, this.chart.options.elements.point.borderWidth);
point._model.backgroundColor = this.getPointBackgroundColor(point, index);
point._model.borderColor = this.getPointBorderColor(point, index);
point._model.borderWidth = this.getPointBorderWidth(point, index);
}
});
}).call(this);
+11
Ver Arquivo
@@ -17,6 +17,16 @@
//Boolean - Whether to animate the rotation of the chart
animateRotate: true,
animateScale: true,
// Need to override these to give a nice default
tooltips: {
callbacks: {
title: function() { return ''; },
label: function(tooltipItem, data) {
return data.labels[tooltipItem.index] + ': ' + tooltipItem.yLabel;
}
}
}
};
Chart.controllers.polarArea = function(chart, datasetIndex) {
@@ -143,6 +153,7 @@
_chart: this.chart.chart,
_datasetIndex: this.index,
_index: index,
_scale: this.chart.scale,
// Desired view properties
_model: reset ? resetModel : {
+5 -20
Ver Arquivo
@@ -167,6 +167,7 @@
// Utility
_datasetIndex: this.index,
_index: index,
_scale: this.chart.scale,
// Desired view properties
_model: {
@@ -196,28 +197,12 @@
point._model.tension
);
point._model.controlPointPreviousX = controlPoints.previous.x;
point._model.controlPointNextX = controlPoints.next.x;
// Prevent the bezier going outside of the bounds of the graph
point._model.controlPointPreviousX = Math.max(Math.min(controlPoints.previous.x, this.chart.chartArea.right), this.chart.chartArea.left);
point._model.controlPointPreviousY = Math.max(Math.min(controlPoints.previous.y, this.chart.chartArea.bottom), this.chart.chartArea.top);
// Cap outer bezier handles to the upper/lower scale bounds
if (controlPoints.next.y > this.chart.chartArea.bottom) {
point._model.controlPointNextY = this.chart.chartArea.bottom;
} else if (controlPoints.next.y < this.chart.chartArea.top) {
point._model.controlPointNextY = this.chart.chartArea.top;
} else {
point._model.controlPointNextY = controlPoints.next.y;
}
// Cap inner bezier handles to the upper/lower scale bounds
if (controlPoints.previous.y > this.chart.chartArea.bottom) {
point._model.controlPointPreviousY = this.chart.chartArea.bottom;
} else if (controlPoints.previous.y < this.chart.chartArea.top) {
point._model.controlPointPreviousY = this.chart.chartArea.top;
} else {
point._model.controlPointPreviousY = controlPoints.previous.y;
}
point._model.controlPointNextX = Math.max(Math.min(controlPoints.next.x, this.chart.chartArea.right), this.chart.chartArea.left);
point._model.controlPointNextY = Math.max(Math.min(controlPoints.next.y, this.chart.chartArea.bottom), this.chart.chartArea.top);
// Now pivot the point for animation
point.pivot();
+51 -36
Ver Arquivo
@@ -23,10 +23,15 @@
this.chart = instance;
this.config = instance.config;
this.data = this.config.data;
this.options = this.config.options = helpers.configMerge(Chart.defaults.global, Chart.defaults[this.config.type], this.config.options || {});
this.id = helpers.uid();
Object.defineProperty(this, 'data', {
get: function() {
return this.config.data;
},
});
//Add the chart instance to the global namespace
Chart.instances[this.id] = this;
@@ -112,7 +117,7 @@
}
},
buildScales: function buildScales() {
// Map of scale ID to scale object so we can lookup later
// Map of scale ID to scale object so we can lookup later
this.scales = {};
// Build the x axes
@@ -123,7 +128,7 @@
var scale = new ScaleClass({
ctx: this.chart.ctx,
options: xAxisOptions,
data: this.data,
chart: this,
id: xAxisOptions.id,
});
@@ -138,7 +143,7 @@
var scale = new ScaleClass({
ctx: this.chart.ctx,
options: yAxisOptions,
data: this.data,
chart: this,
id: yAxisOptions.id,
});
@@ -152,8 +157,7 @@
var scale = new ScaleClass({
ctx: this.chart.ctx,
options: this.options.scale,
data: this.data,
chart: this.chart,
chart: this,
});
this.scale = scale;
@@ -170,18 +174,22 @@
if (!dataset.type) {
dataset.type = this.config.type;
}
var type = dataset.type;
types.push(type);
if (dataset.controller) {
dataset.controller.updateIndex(datasetIndex);
return;
}
dataset.controller = new Chart.controllers[type](this, datasetIndex);
if (resetNewControllers) {
dataset.controller.reset();
}
}, this);
if (types.length > 1) {
for (var i = 1; i < types.length; i++) {
if (types[i] != types[i - 1]) {
@@ -199,6 +207,9 @@
},
update: function update(animationDuration, lazy) {
// In case the entire data object changed
this.tooltip._data = this.data;
Chart.scaleService.update(this, this.chart.width, this.chart.height);
// Make sure dataset controllers are updated and new controllers are reset
@@ -294,13 +305,25 @@
var eventPosition = helpers.getRelativePosition(e, this.chart);
var elementsArray = [];
helpers.each(this.data.datasets, function(dataset, datasetIndex) {
if (helpers.isDatasetVisible(dataset)) {
helpers.each(dataset.metaData, function(element, index) {
if (element.inLabelRange(eventPosition.x, eventPosition.y)) {
elementsArray.push(element);
var found = (function(){
for (var i = 0; i < this.data.datasets.length; i++) {
if (helpers.isDatasetVisible(this.data.datasets[i])) {
for (var j = 0; j < this.data.datasets[i].metaData.length; j++) {
if (this.data.datasets[i].metaData[j].inRange(eventPosition.x, eventPosition.y)) {
return this.data.datasets[i].metaData[j];
}
}
}, this);
}
}
}).call(this);
if(!found){
return elementsArray;
}
helpers.each(this.data.datasets, function(dataset, dsIndex){
if(helpers.isDatasetVisible(dataset)){
elementsArray.push(dataset.metaData[found._index]);
}
}, this);
@@ -375,7 +398,8 @@
// Find Active Elements for hover and tooltips
if (e.type == 'mouseout') {
this.active = this.tooltipActive = [];
this.active = [];
this.tooltipActive = [];
} else {
this.active = function() {
switch (this.options.hover.mode) {
@@ -426,7 +450,8 @@
case 'label':
case 'dataset':
for (var i = 0; i < this.lastActive.length; i++) {
this.data.datasets[this.lastActive[i]._datasetIndex].controller.removeHoverStyle(this.lastActive[i], this.lastActive[i]._datasetIndex, this.lastActive[i]._index);
if (this.lastActive[i])
this.data.datasets[this.lastActive[i]._datasetIndex].controller.removeHoverStyle(this.lastActive[i], this.lastActive[i]._datasetIndex, this.lastActive[i]._index);
}
break;
default:
@@ -443,7 +468,8 @@
case 'label':
case 'dataset':
for (var j = 0; j < this.active.length; j++) {
this.data.datasets[this.active[j]._datasetIndex].controller.setHoverStyle(this.active[j]);
if (this.active[j])
this.data.datasets[this.active[j]._datasetIndex].controller.setHoverStyle(this.active[j]);
}
break;
default:
@@ -457,20 +483,8 @@
// The usual updates
this.tooltip.initialize();
// Active
if (this.tooltipActive.length) {
this.tooltip._model.opacity = 1;
helpers.extend(this.tooltip, {
_active: this.tooltipActive,
});
this.tooltip.update();
} else {
// Inactive
this.tooltip._model.opacity = 0;
}
this.tooltip._active = this.tooltipActive;
this.tooltip.update();
}
// Hover animations
@@ -492,16 +506,17 @@
}, this);
// If entering, leaving, or changing elements, animate the change via pivot
if ((!this.lastActive.length && this.active.length) ||
(this.lastActive.length && !this.active.length) ||
(this.lastActive.length && this.active.length && changed) ||
(!this.lastTooltipActive.length && this.tooltipActive.length) ||
(this.lastTooltipActive.length && !this.tooltipActive.length) ||
(this.lastTooltipActive.length && this.tooltipActive.length && changed)) {
if ((this.lastActive.length !== this.active.length) ||
(this.lastTooltipActive.length !== this.tooltipActive.length) ||
changed) {
this.stop();
// We only need to render at this point. Updating will cause scales to be recomputed generating flicker & using more
if (this.options.tooltips.enabled || this.options.tooltips.custom) {
this.tooltip.update(true);
}
// We only need to render at this point. Updating will cause scales to be recomputed generating flicker & using more
// memory than necessary.
this.render(this.options.hover.animationDuration, true);
}
+2 -3
Ver Arquivo
@@ -38,7 +38,7 @@
// Init if doesn't exist
else if (!this._view[key]) {
if (typeof value === 'number') {
if (typeof value === 'number' && isNaN(this._view[key]) === false) {
this._view[key] = value * ease;
} else {
this._view[key] = value || null;
@@ -61,14 +61,13 @@
}
// Number transitions
else if (typeof value === 'number') {
var startVal = this._start[key] !== undefined ? this._start[key] : 0;
var startVal = this._start[key] !== undefined && isNaN(this._start[key]) === false ? this._start[key] : 0;
this._view[key] = ((this._model[key] - startVal) * ease) + startVal;
}
// Everything else
else {
this._view[key] = value;
}
}, this);
if (ease === 1) {
+24 -22
Ver Arquivo
@@ -321,27 +321,29 @@
aliasPixel = helpers.aliasPixel = function(pixelWidth) {
return (pixelWidth % 2 === 0) ? 0 : 0.5;
},
splineCurve = helpers.splineCurve = function(FirstPoint, MiddlePoint, AfterPoint, t) {
splineCurve = helpers.splineCurve = function(firstPoint, middlePoint, afterPoint, t) {
//Props to Rob Spencer at scaled innovation for his post on splining between points
//http://scaledinnovation.com/analytics/splines/aboutSplines.html
// This function must also respect "skipped" points
var previous = FirstPoint,
current = MiddlePoint,
next = AfterPoint;
var previous = firstPoint.skip ? middlePoint : firstPoint,
current = middlePoint,
next = afterPoint.skip ? middlePoint : afterPoint;
if (previous.skip) {
previous = current;
}
if (next.skip) {
next = current;
}
var d01 = Math.sqrt(Math.pow(current.x - previous.x, 2) + Math.pow(current.y - previous.y, 2));
var d12 = Math.sqrt(Math.pow(next.x - current.x, 2) + Math.pow(next.y - current.y, 2));
var s01 = d01 / (d01 + d12);
var s12 = d12 / (d01 + d12);
// If all points are the same, s01 & s02 will be inf
s01 = isNaN(s01) ? 0 : s01;
s12 = isNaN(s12) ? 0 : s12;
var fa = t * s01; // scaling factor for triangle Ta
var fb = t * s12;
var d01 = Math.sqrt(Math.pow(current.x - previous.x, 2) + Math.pow(current.y - previous.y, 2)),
d12 = Math.sqrt(Math.pow(next.x - current.x, 2) + Math.pow(next.y - current.y, 2)),
fa = t * d01 / (d01 + d12), // scaling factor for triangle Ta
fb = t * d12 / (d01 + d12);
return {
previous: {
x: current.x - fa * (next.x - previous.x),
@@ -622,7 +624,7 @@
canvas = evt.currentTarget || evt.srcElement,
boundingRect = canvas.getBoundingClientRect();
if (e.touches) {
if (e.touches && e.touches.length > 0) {
mouseX = e.touches[0].clientX;
mouseY = e.touches[0].clientY;
@@ -632,7 +634,7 @@
}
// Scale mouse coordinates into canvas coordinates
// by following the pattern laid out by 'jerryj' in the comments of
// by following the pattern laid out by 'jerryj' in the comments of
// http://www.html5canvastutorials.com/advanced/html5-canvas-mouse-coordinates/
// We divide by the current device pixel ratio, because the canvas is scaled up by that amount in each direction. However
@@ -739,12 +741,12 @@
var ctx = chart.ctx;
var width = chart.canvas.width;
var height = chart.canvas.height;
chart.currentDevicePixelRatio = window.devicePixelRatio || 1;
var pixelRatio = chart.currentDevicePixelRatio = window.devicePixelRatio || 1;
if (window.devicePixelRatio !== 1) {
ctx.canvas.height = height * window.devicePixelRatio;
ctx.canvas.width = width * window.devicePixelRatio;
ctx.scale(window.devicePixelRatio, window.devicePixelRatio);
if (pixelRatio !== 1) {
ctx.canvas.height = height * pixelRatio;
ctx.canvas.width = width * pixelRatio;
ctx.scale(pixelRatio, pixelRatio);
ctx.canvas.style.width = width + 'px';
ctx.canvas.style.height = height + 'px';
@@ -752,7 +754,7 @@
// Store the device pixel ratio so that we can go backwards in `destroy`.
// The devicePixelRatio changes with zoom, so there are no guarantees that it is the same
// when destroy is called
chart.originalDevicePixelRatio = chart.originalDevicePixelRatio || window.devicePixelRatio;
chart.originalDevicePixelRatio = chart.originalDevicePixelRatio || pixelRatio;
}
},
//-- Canvas methods
+1 -1
Ver Arquivo
@@ -79,7 +79,7 @@
responsive: true,
responsiveAnimationDuration: 0,
maintainAspectRatio: true,
events: ["mousemove", "mouseout", "click", "touchstart", "touchmove", "touchend"],
events: ["mousemove", "mouseout", "click", "touchstart", "touchmove"],
hover: {
onHover: null,
mode: 'single',
+25 -13
Ver Arquivo
@@ -10,7 +10,7 @@
// grid line settings
gridLines: {
show: true,
display: true,
color: "rgba(0, 0, 0, 0.1)",
lineWidth: 1,
drawOnChartArea: true,
@@ -31,7 +31,7 @@
labelString: '',
// display property
show: false,
display: false,
},
// label settings
@@ -46,7 +46,7 @@
mirror: false,
padding: 10,
reverse: false,
show: true,
display: true,
callback: function(value) {
return '' + value;
},
@@ -231,18 +231,18 @@
if (this.isHorizontal()) {
this.minSize.width = this.maxWidth; // fill all the width
} else {
this.minSize.width = this.options.gridLines.show && this.options.display ? 10 : 0;
this.minSize.width = this.options.gridLines.display && this.options.display ? 10 : 0;
}
// height
if (this.isHorizontal()) {
this.minSize.height = this.options.gridLines.show && this.options.display ? 10 : 0;
this.minSize.height = this.options.gridLines.display && this.options.display ? 10 : 0;
} else {
this.minSize.height = this.maxHeight; // fill all the height
}
// Are we showing a title for the scale?
if (this.options.scaleLabel.show) {
if (this.options.scaleLabel.display) {
if (this.isHorizontal()) {
this.minSize.height += (this.options.scaleLabel.fontSize * 1.5);
} else {
@@ -250,7 +250,7 @@
}
}
if (this.options.ticks.show && this.options.display) {
if (this.options.ticks.display && this.options.display) {
// Don't bother fitting the ticks if we are not showing them
var labelFont = helpers.fontString(this.options.ticks.fontSize,
this.options.ticks.fontStyle, this.options.ticks.fontFamily);
@@ -259,6 +259,8 @@
// A horizontal axis is more constrained by the height.
var maxLabelHeight = this.maxHeight - this.minSize.height;
var longestLabelWidth = helpers.longestText(this.ctx, labelFont, this.ticks);
// TODO - improve this calculation
var labelHeight = (Math.sin(helpers.toRadians(this.labelRotation)) * longestLabelWidth) + 1.5 * this.options.ticks.fontSize;
this.minSize.height = Math.min(this.maxHeight, this.minSize.height + labelHeight);
@@ -280,6 +282,11 @@
var maxLabelWidth = this.maxWidth - this.minSize.width;
var largestTextWidth = helpers.longestText(this.ctx, labelFont, this.ticks);
// Account for padding
if (!this.options.ticks.mirror) {
largestTextWidth += this.options.ticks.padding;
}
if (largestTextWidth < maxLabelWidth) {
// We don't need all the room
this.minSize.width += largestTextWidth;
@@ -404,7 +411,7 @@
var xLineValue = this.getPixelForTick(index); // xvalues for grid lines
var xLabelValue = this.getPixelForTick(index, this.options.gridLines.offsetGridLines); // x values for ticks (need to consider offsetLabel option)
if (this.options.gridLines.show) {
if (this.options.gridLines.display) {
if (index === (typeof this.zeroLineIndex !== 'undefined' ? this.zeroLineIndex : 0)) {
// Draw the first index specially
this.ctx.lineWidth = this.options.gridLines.zeroLineWidth;
@@ -436,7 +443,7 @@
this.ctx.stroke();
}
if (this.options.ticks.show) {
if (this.options.ticks.display) {
this.ctx.save();
this.ctx.translate(xLabelValue, (isRotated) ? this.top + 12 : this.options.position === "top" ? this.bottom - 10 : this.top + 10);
this.ctx.rotate(helpers.toRadians(this.labelRotation) * -1);
@@ -448,7 +455,7 @@
}
}, this);
if (this.options.scaleLabel.show) {
if (this.options.scaleLabel.display) {
// Draw the scale label
this.ctx.textAlign = "center";
this.ctx.textBaseline = 'middle';
@@ -467,9 +474,14 @@
var xTickEnd = this.options.position == "right" ? this.left + 5 : this.right;
helpers.each(this.ticks, function(label, index) {
// If the callback returned a null or undefined value, do not draw this line
if (label === undefined || label === null) {
return;
}
var yLineValue = this.getPixelForTick(index); // xvalues for grid lines
if (this.options.gridLines.show) {
if (this.options.gridLines.display) {
if (index === (typeof this.zeroLineIndex !== 'undefined' ? this.zeroLineIndex : 0)) {
// Draw the first index specially
this.ctx.lineWidth = this.options.gridLines.zeroLineWidth;
@@ -501,7 +513,7 @@
this.ctx.stroke();
}
if (this.options.ticks.show) {
if (this.options.ticks.display) {
var xLabelValue;
var yLabelValue = this.getPixelForTick(index, this.options.gridLines.offsetGridLines); // x values for ticks (need to consider offsetLabel option)
@@ -536,7 +548,7 @@
}
}, this);
if (this.options.scaleLabel.show) {
if (this.options.scaleLabel.display) {
// Draw the scale label
scaleLabelX = this.options.position == 'left' ? this.left + (this.options.scaleLabel.fontSize / 2) : this.right - (this.options.scaleLabel.fontSize / 2);
scaleLabelY = this.top + ((this.bottom - this.top) / 2);
+151 -99
Ver Arquivo
@@ -38,23 +38,39 @@
xOffset: 10,
multiKeyBackground: '#fff',
callbacks: {
// Args are: (tooltipItems, data)
beforeTitle: helpers.noop,
title: function(xLabel, yLabel, index, datasetIndex, data) {
// Pick first label for now
return helpers.isArray(xLabel) ? xLabel[0] : xLabel;
title: function(tooltipItems, data) {
// Pick first xLabel for now
var title = '';
if (tooltipItems.length > 0) {
if (tooltipItems[0].xLabel) {
title = tooltipItems[0].xLabel;
} else if (data.labels.length > 0 && tooltipItems[0].index < data.labels.length) {
title = data.labels[tooltipItems[0].index];
}
}
return title;
},
afterTitle: helpers.noop,
// Args are: (tooltipItems, data)
beforeBody: helpers.noop,
// Args are: (tooltipItem, data)
beforeLabel: helpers.noop,
label: function(xLabel, yLabel, index, datasetIndex, data) {
return this._data.datasets[datasetIndex].label + ': ' + yLabel;
label: function(tooltipItem, data) {
var datasetLabel = data.datasets[tooltipItem.datasetIndex].label || '';
return datasetLabel + ': ' + tooltipItem.yLabel;
},
afterLabel: helpers.noop,
// Args are: (tooltipItems, data)
afterBody: helpers.noop,
// Args are: (tooltipItems, data)
beforeFooter: helpers.noop,
footer: helpers.noop,
afterFooter: helpers.noop,
@@ -88,9 +104,9 @@
bodyColor: options.tooltips.bodyColor,
_bodyFontFamily: options.tooltips.bodyFontFamily,
_bodyFontStyle: options.tooltips.bodyFontStyle,
_bodyAlign: options.tooltips.bodyAlign,
bodyFontSize: options.tooltips.bodyFontSize,
bodySpacing: options.tooltips.bodySpacing,
_bodposition: options.tooltips.bodposition,
// Title
titleColor: options.tooltips.titleColor,
@@ -120,7 +136,8 @@
});
},
// Get the title
// Get the title
// Args are: (tooltipItem, data)
getTitle: function() {
var beforeTitle = this._options.tooltips.callbacks.beforeTitle.apply(this, arguments),
title = this._options.tooltips.callbacks.title.apply(this, arguments),
@@ -134,59 +151,35 @@
return lines;
},
getBeforeBody: function(xLabel, yLabel, index, datasetIndex, data) {
var lines = this._options.tooltips.callbacks.beforeBody.call(this, xLabel, yLabel, index, datasetIndex, data);
// Args are: (tooltipItem, data)
getBeforeBody: function() {
var lines = this._options.tooltips.callbacks.beforeBody.call(this, arguments);
return helpers.isArray(lines) ? lines : [lines];
},
getBody: function(xLabel, yLabel, index, datasetIndex) {
// Args are: (tooltipItem, data)
getBody: function(tooltipItems, data) {
var lines = [];
var beforeLabel,
afterLabel,
label;
helpers.each(tooltipItems, function(bodyItem) {
var beforeLabel = this._options.tooltips.callbacks.beforeLabel.call(this, bodyItem, data) || '';
var bodyLabel = this._options.tooltips.callbacks.label.call(this, bodyItem, data) || '';
var afterLabel = this._options.tooltips.callbacks.afterLabel.call(this, bodyItem, data) || '';
if (helpers.isArray(xLabel)) {
var labels = [];
// Run EACH label pair through the label callback this time.
for (var i = 0; i < xLabel.length; i++) {
beforeLabel = this._options.tooltips.callbacks.beforeLabel.call(this, xLabel[i], yLabel[i], index, datasetIndex);
afterLabel = this._options.tooltips.callbacks.afterLabel.call(this, xLabel[i], yLabel[i], index, datasetIndex);
labels.push((beforeLabel ? beforeLabel : '') + this._options.tooltips.callbacks.label.call(this, xLabel[i], yLabel[i], index, datasetIndex) + (afterLabel ? afterLabel : ''));
}
if (labels.length) {
lines = lines.concat(labels);
}
} else {
// Run the single label through the callback
beforeLabel = this._options.tooltips.callbacks.beforeLabel.apply(this, arguments);
label = this._options.tooltips.callbacks.label.apply(this, arguments);
afterLabel = this._options.tooltips.callbacks.afterLabel.apply(this, arguments);
if (beforeLabel || label || afterLabel) {
lines.push((beforeLabel ? afterLabel : '') + label + (afterLabel ? afterLabel : ''));
}
}
lines.push(beforeLabel + bodyLabel + afterLabel);
}, this);
return lines;
},
getAfterBody: function(xLabel, yLabel, index, datasetIndex, data) {
var lines = this._options.tooltips.callbacks.afterBody.call(this, xLabel, yLabel, index, datasetIndex, data);
// Args are: (tooltipItem, data)
getAfterBody: function() {
var lines = this._options.tooltips.callbacks.afterBody.call(this, arguments);
return helpers.isArray(lines) ? lines : [lines];
},
// Get the footer and beforeFooter and afterFooter lines
// Args are: (tooltipItem, data)
getFooter: function() {
var beforeFooter = this._options.tooltips.callbacks.beforeFooter.apply(this, arguments);
var footer = this._options.tooltips.callbacks.footer.apply(this, arguments);
@@ -200,68 +193,118 @@
return lines;
},
update: function() {
getAveragePosition: function(elements){
if(!elements.length){
return false;
}
var xPositions = [];
var yPositions = [];
helpers.each(elements, function(el){
if(el) {
var pos = el.tooltipPosition();
xPositions.push(pos.x);
yPositions.push(pos.y);
}
});
var x = 0, y = 0;
for (var i = 0; i < xPositions.length; i++) {
x += xPositions[i];
y += yPositions[i];
}
return {
x: Math.round(x / xPositions.length),
y: Math.round(y / xPositions.length)
};
},
update: function(changed) {
var ctx = this._chart.ctx;
var element = this._active[0],
xLabel,
yLabel,
labelColors = [],
tooltipPosition;
if(this._active.length){
this._model.opacity = 1;
if (this._options.tooltips.mode == 'single') {
var element = this._active[0],
labelColors = [],
tooltipPosition;
xLabel = element._xScale.getLabelForIndex(element._index, element._datasetIndex);
yLabel = element._yScale.getLabelForIndex(element._index, element._datasetIndex);
tooltipPosition = this._active[0].tooltipPosition();
var tooltipItems = [];
} else {
if (this._options.tooltips.mode == 'single') {
var yScale = element._yScale || element._scale; // handle radar || polarArea charts
tooltipItems.push({
xLabel: element._xScale ? element._xScale.getLabelForIndex(element._index, element._datasetIndex) : '',
yLabel: yScale ? yScale.getLabelForIndex(element._index, element._datasetIndex) : '',
index: element._index,
datasetIndex: element._datasetIndex,
});
tooltipPosition = this.getAveragePosition(this._active);
} else {
helpers.each(this._data.datasets, function(dataset, datasetIndex) {
if (!helpers.isDatasetVisible(dataset)) {
return;
}
var currentElement = dataset.metaData[element._index];
if (currentElement) {
var yScale = element._yScale || element._scale; // handle radar || polarArea charts
xLabel = [];
yLabel = [];
tooltipItems.push({
xLabel: currentElement._xScale ? currentElement._xScale.getLabelForIndex(currentElement._index, currentElement._datasetIndex) : '',
yLabel: yScale ? yScale.getLabelForIndex(currentElement._index, currentElement._datasetIndex) : '',
index: element._index,
datasetIndex: datasetIndex,
});
}
});
helpers.each(this._data.datasets, function(dataset, datasetIndex) {
if (!helpers.isDatasetVisible(dataset)) {
return;
}
xLabel.push(element._xScale.getLabelForIndex(element._index, datasetIndex));
yLabel.push(element._yScale.getLabelForIndex(element._index, datasetIndex));
helpers.each(this._active, function(active, i) {
if (active) {
labelColors.push({
borderColor: active._view.borderColor,
backgroundColor: active._view.backgroundColor
});
}
}, this);
tooltipPosition = this.getAveragePosition(this._active);
tooltipPosition.y = this._active[0]._yScale.getPixelForDecimal(0.5);
}
// Build the Text Lines
helpers.extend(this._model, {
title: this.getTitle(tooltipItems, this._data),
beforeBody: this.getBeforeBody(tooltipItems, this._data),
body: this.getBody(tooltipItems, this._data),
afterBody: this.getAfterBody(tooltipItems, this._data),
footer: this.getFooter(tooltipItems, this._data),
});
helpers.each(this._active, function(active, i) {
labelColors.push({
borderColor: active._view.borderColor,
backgroundColor: active._view.backgroundColor
});
}, this);
tooltipPosition = this._active[0].tooltipPosition();
tooltipPosition.y = this._active[0]._yScale.getPixelForDecimal(0.5);
helpers.extend(this._model, {
x: Math.round(tooltipPosition.x),
y: Math.round(tooltipPosition.y),
caretPadding: tooltipPosition.padding,
labelColors: labelColors,
});
}
else{
this._model.opacity = 0;
}
// Build the Text Lines
helpers.extend(this._model, {
title: this.getTitle(xLabel, yLabel, element._index, element._datasetIndex, this._data),
beforeBody: this.getBeforeBody(xLabel, yLabel, element._index, element._datasetIndex, this._data),
body: this.getBody(xLabel, yLabel, element._index, element._datasetIndex, this._data),
afterBody: this.getAfterBody(xLabel, yLabel, element._index, element._datasetIndex, this._data),
footer: this.getFooter(xLabel, yLabel, element._index, element._datasetIndex, this._data),
});
helpers.extend(this._model, {
x: Math.round(tooltipPosition.x),
y: Math.round(tooltipPosition.y),
caretPadding: tooltipPosition.padding,
labelColors: labelColors,
});
if (changed && this._options.tooltips.custom) {
this._options.tooltips.custom.call(this, this._model);
}
return this;
},
draw: function() {
var ctx = this._chart.ctx;
var vm = this._view;
@@ -349,8 +392,11 @@
// Draw Background
// IE11/Edge does not like very small opacities, so snap to 0
var opacity = Math.abs(vm.opacity < 1e-3) ? 0 : vm.opacity;
if (this._options.tooltips.enabled) {
ctx.fillStyle = helpers.color(vm.backgroundColor).alpha(vm.opacity).rgbString();
ctx.fillStyle = helpers.color(vm.backgroundColor).alpha(opacity).rgbString();
helpers.drawRoundedRectangle(ctx, tooltipX, tooltipY, tooltipWidth, tooltipHeight, vm.cornerRadius);
ctx.fill();
}
@@ -358,7 +404,7 @@
// Draw Caret
if (this._options.tooltips.enabled) {
ctx.fillStyle = helpers.color(vm.backgroundColor).alpha(vm.opacity).rgbString();
ctx.fillStyle = helpers.color(vm.backgroundColor).alpha(opacity).rgbString();
if (vm.xAlign == 'left') {
@@ -390,7 +436,7 @@
if (vm.title.length) {
ctx.textAlign = vm._titleAlign;
ctx.textBaseline = "top";
ctx.fillStyle = helpers.color(vm.titleColor).alpha(vm.opacity).rgbString();
ctx.fillStyle = helpers.color(vm.titleColor).alpha(opacity).rgbString();
ctx.font = helpers.fontString(vm.titleFontSize, vm._titleFontStyle, vm._titleFontFamily);
helpers.each(vm.title, function(title, i) {
@@ -406,7 +452,7 @@
// Body
ctx.textAlign = vm._bodyAlign;
ctx.textBaseline = "top";
ctx.fillStyle = helpers.color(vm.bodyColor).alpha(vm.opacity).rgbString();
ctx.fillStyle = helpers.color(vm.bodyColor).alpha(opacity).rgbString();
ctx.font = helpers.fontString(vm.bodyFontSize, vm._bodyFontStyle, vm._bodyFontFamily);
// Before Body
@@ -420,13 +466,19 @@
// Draw Legend-like boxes if needed
if (this._options.tooltips.mode != 'single') {
ctx.fillStyle = helpers.color(vm.labelColors[i].borderColor).alpha(vm.opacity).rgbString();
// Fill a white rect so that colours merge nicely if the opacity is < 1
ctx.fillStyle = helpers.color('#FFFFFF').alpha(opacity).rgbaString();
ctx.fillRect(xBase, yBase, vm.bodyFontSize, vm.bodyFontSize);
ctx.fillStyle = helpers.color(vm.labelColors[i].backgroundColor).alpha(vm.opacity).rgbString();
// Border
ctx.strokeStyle = helpers.color(vm.labelColors[i].borderColor).alpha(opacity).rgbaString();
ctx.strokeRect(xBase, yBase, vm.bodyFontSize, vm.bodyFontSize);
// Inner square
ctx.fillStyle = helpers.color(vm.labelColors[i].backgroundColor).alpha(opacity).rgbaString();
ctx.fillRect(xBase + 1, yBase + 1, vm.bodyFontSize - 2, vm.bodyFontSize - 2);
ctx.fillStyle = helpers.color(vm.bodyColor).alpha(vm.opacity).rgbString(); // Return fill style for text
ctx.fillStyle = helpers.color(vm.bodyColor).alpha(opacity).rgbaString(); // Return fill style for text
}
// Body Line
@@ -452,7 +504,7 @@
ctx.textAlign = vm._footerAlign;
ctx.textBaseline = "top";
ctx.fillStyle = helpers.color(vm.footerColor).alpha(vm.opacity).rgbString();
ctx.fillStyle = helpers.color(vm.footerColor).alpha(opacity).rgbString();
ctx.font = helpers.fontString(vm.footerFontSize, vm._footerFontStyle, vm._footerFontFamily);
helpers.each(vm.footer, function(footer, i) {
+86 -104
Ver Arquivo
@@ -29,64 +29,38 @@
fill: true, // do we fill in the area between the line and its base axis
};
Chart.elements.Line = Chart.Element.extend({
lineToNextPoint: function(previousPoint, point, nextPoint, skipHandler, previousSkipHandler) {
var ctx = this._chart.ctx;
if (point._view.skip) {
skipHandler.call(this, previousPoint, point, nextPoint);
} else if (previousPoint._view.skip) {
previousSkipHandler.call(this, previousPoint, point, nextPoint);
} else {
// Line between points
ctx.bezierCurveTo(
previousPoint._view.controlPointNextX,
previousPoint._view.controlPointNextY,
point._view.controlPointPreviousX,
point._view.controlPointPreviousY,
point._view.x,
point._view.y
);
}
},
draw: function() {
var _this = this;
var vm = this._view;
var ctx = this._chart.ctx;
var first = this._children[0];
var last = this._children[this._children.length - 1];
ctx.save();
// Draw the background first (so the border is always on top)
helpers.each(this._children, function(point, index) {
var previous = helpers.previousItem(this._children, index);
var next = helpers.nextItem(this._children, index);
// First point moves to it's starting position no matter what
if (!index) {
ctx.moveTo(point._view.x, vm.scaleZero);
}
// Skip this point, draw to scaleZero, move to next point, and draw to next point
if (point._view.skip && !this.loop) {
ctx.lineTo(previous._view.x, vm.scaleZero);
ctx.moveTo(next._view.x, vm.scaleZero);
return;
}
// The previous line was skipped, so just draw a normal straight line to the point
if (previous._view.skip) {
ctx.lineTo(point._view.x, point._view.y);
return;
}
// Draw a bezier to point
if (vm.tension > 0 && index) {
//ctx.lineTo(point._view.x, point._view.y);
ctx.bezierCurveTo(
previous._view.controlPointNextX,
previous._view.controlPointNextY,
point._view.controlPointPreviousX,
point._view.controlPointPreviousY,
point._view.x,
point._view.y
);
return;
}
// Draw a straight line to the point
ctx.lineTo(point._view.x, point._view.y);
}, this);
// For radial scales, loop back around to the first point
if (this._loop) {
// Draw a bezier line
if (vm.tension > 0 && !first._view.skip) {
function loopBackToStart(drawLineToCenter) {
if (!first._view.skip && !last._view.skip) {
// Draw a bezier line from last to first
ctx.bezierCurveTo(
last._view.controlPointNextX,
last._view.controlPointNextY,
@@ -95,23 +69,68 @@
first._view.x,
first._view.y
);
return;
} else if (drawLineToCenter) {
// Go to center
ctx.lineTo(_this._view.scaleZero.x, _this._view.scaleZero.y);
}
// Draw a straight line
ctx.lineTo(first._view.x, first._view.y);
}
ctx.save();
// If we had points and want to fill this line, do so.
if (this._children.length > 0 && vm.fill) {
//Round off the line by going to the base of the chart, back to the start, then fill.
ctx.lineTo(this._children[this._children.length - 1]._view.x, vm.scaleZero);
ctx.lineTo(this._children[0]._view.x, vm.scaleZero);
// Draw the background first (so the border is always on top)
ctx.beginPath();
helpers.each(this._children, function(point, index) {
var previous = helpers.previousItem(this._children, index);
var next = helpers.nextItem(this._children, index);
// First point moves to it's starting position no matter what
if (index === 0) {
if (this._loop) {
ctx.moveTo(vm.scaleZero.x, vm.scaleZero.y);
} else {
ctx.moveTo(point._view.x, vm.scaleZero);
}
if (point._view.skip) {
if (!this._loop) {
ctx.moveTo(next._view.x, this._view.scaleZero);
}
} else {
ctx.lineTo(point._view.x, point._view.y);
}
} else {
this.lineToNextPoint(previous, point, next, function(previousPoint, point, nextPoint) {
if (this._loop) {
// Go to center
ctx.lineTo(this._view.scaleZero.x, this._view.scaleZero.y);
} else {
ctx.lineTo(previousPoint._view.x, this._view.scaleZero);
ctx.moveTo(nextPoint._view.x, this._view.scaleZero);
}
}, function(previousPoint, point, nextPoint) {
// If we skipped the last point, draw a line to ourselves so that the fill is nice
ctx.lineTo(point._view.x, point._view.y);
});
}
}, this);
// For radial scales, loop back around to the first point
if (this._loop) {
loopBackToStart(true);
} else {
//Round off the line by going to the base of the chart, back to the start, then fill.
ctx.lineTo(this._children[this._children.length - 1]._view.x, vm.scaleZero);
ctx.lineTo(this._children[0]._view.x, vm.scaleZero);
}
ctx.fillStyle = vm.backgroundColor || Chart.defaults.global.defaultColor;
ctx.closePath();
ctx.fill();
}
// Now draw the line between all the points with any borders
ctx.lineCap = vm.borderCapStyle || Chart.defaults.global.elements.line.borderCapStyle;
@@ -130,57 +149,20 @@
var previous = helpers.previousItem(this._children, index);
var next = helpers.nextItem(this._children, index);
if (!index) {
ctx.moveTo(point._view.x, vm.scaleZero);
}
// Skip this point and move to the next points zeroPoint
if (point._view.skip && !this.loop) {
ctx.moveTo(next._view.x, vm.scaleZero);
return;
}
// Previous point was skipped, just move to the point
if (previous._view.skip) {
if (index === 0) {
ctx.moveTo(point._view.x, point._view.y);
return;
} else {
this.lineToNextPoint(previous, point, next, function(previousPoint, point, nextPoint) {
ctx.moveTo(nextPoint._view.x, nextPoint._view.y);
}, function(previousPoint, point, nextPoint) {
// If we skipped the last point, move up to our point preventing a line from being drawn
ctx.moveTo(point._view.x, point._view.y);
});
}
// Draw a bezier line to the point
if (vm.tension > 0 && index) {
ctx.bezierCurveTo(
previous._view.controlPointNextX,
previous._view.controlPointNextY,
point._view.controlPointPreviousX,
point._view.controlPointPreviousY,
point._view.x,
point._view.y
);
return;
}
// Draw a straight line to the point
ctx.lineTo(point._view.x, point._view.y);
}, this);
if (this._loop && !first._view.skip) {
// Draw a bezier line to the first point
if (vm.tension > 0) {
ctx.bezierCurveTo(
last._view.controlPointNextX,
last._view.controlPointNextY,
first._view.controlPointPreviousX,
first._view.controlPointPreviousY,
first._view.x,
first._view.y
);
return;
}
// Draw a straight line to the first point
ctx.lineTo(first._view.x, first._view.y);
if (this._loop) {
loopBackToStart();
}
ctx.stroke();
+3 -3
Ver Arquivo
@@ -12,7 +12,7 @@
var DatasetScale = Chart.Scale.extend({
buildTicks: function(index) {
this.ticks = this.data.labels;
this.ticks = this.chart.data.labels;
},
getLabelForIndex: function(index, datasetIndex) {
@@ -23,7 +23,7 @@
getPixelForValue: function(value, index, datasetIndex, includeOffset) {
if (this.isHorizontal()) {
var innerWidth = this.width - (this.paddingLeft + this.paddingRight);
var valueWidth = innerWidth / Math.max((this.data.labels.length - ((this.options.gridLines.offsetGridLines) ? 0 : 1)), 1);
var valueWidth = innerWidth / Math.max((this.chart.data.labels.length - ((this.options.gridLines.offsetGridLines) ? 0 : 1)), 1);
var widthOffset = (valueWidth * index) + this.paddingLeft;
if (this.options.gridLines.offsetGridLines && includeOffset) {
@@ -33,7 +33,7 @@
return this.left + Math.round(widthOffset);
} else {
var innerHeight = this.height - (this.paddingTop + this.paddingBottom);
var valueHeight = innerHeight / Math.max((this.data.labels.length - ((this.options.gridLines.offsetGridLines) ? 0 : 1)), 1);
var valueHeight = innerHeight / Math.max((this.chart.data.labels.length - ((this.options.gridLines.offsetGridLines) ? 0 : 1)), 1);
var heightOffset = (valueHeight * index) + this.paddingTop;
if (this.options.gridLines.offsetGridLines && includeOffset) {
+43 -20
Ver Arquivo
@@ -42,15 +42,25 @@
this.min = null;
this.max = null;
var positiveValues = [];
var negativeValues = [];
if (this.options.stacked) {
helpers.each(this.data.datasets, function(dataset) {
var valuesPerType = {};
helpers.each(this.chart.data.datasets, function(dataset) {
if (valuesPerType[dataset.type] === undefined) {
valuesPerType[dataset.type] = {
positiveValues: [],
negativeValues: [],
};
}
// Store these per type
var positiveValues = valuesPerType[dataset.type].positiveValues;
var negativeValues = valuesPerType[dataset.type].negativeValues;
if (helpers.isDatasetVisible(dataset) && (this.isHorizontal() ? dataset.xAxisID === this.id : dataset.yAxisID === this.id)) {
helpers.each(dataset.data, function(rawValue, index) {
var value = this.getRightValue(rawValue);
var value = +this.getRightValue(rawValue);
if (isNaN(value)) {
return;
}
@@ -71,15 +81,19 @@
}
}, this);
var values = positiveValues.concat(negativeValues);
this.min = helpers.min(values);
this.max = helpers.max(values);
helpers.each(valuesPerType, function(valuesForType) {
var values = valuesForType.positiveValues.concat(valuesForType.negativeValues);
var minVal = helpers.min(values);
var maxVal = helpers.max(values);
this.min = this.min === null ? minVal : Math.min(this.min, minVal);
this.max = this.max === null ? maxVal : Math.max(this.max, maxVal);
}, this);
} else {
helpers.each(this.data.datasets, function(dataset) {
helpers.each(this.chart.data.datasets, function(dataset) {
if (helpers.isDatasetVisible(dataset) && (this.isHorizontal() ? dataset.xAxisID === this.id : dataset.yAxisID === this.id)) {
helpers.each(dataset.data, function(rawValue, index) {
var value = this.getRightValue(rawValue);
var value = +this.getRightValue(rawValue);
if (isNaN(value)) {
return;
}
@@ -100,12 +114,6 @@
}, this);
}
if (this.min === this.max) {
this.min--;
this.max++;
}
// Then calulate the ticks
this.ticks = [];
@@ -117,10 +125,12 @@
var maxTicks;
if (this.isHorizontal()) {
maxTicks = Math.min(11, Math.ceil(this.width / 50));
maxTicks = Math.min(this.options.ticks.maxTicksLimit ? this.options.ticks.maxTicksLimit : 11,
Math.ceil(this.width / 50));
} else {
// The factor of 2 used to scale the font size has been experimentally determined.
maxTicks = Math.min(11, Math.ceil(this.height / (2 * this.options.ticks.fontSize)));
maxTicks = Math.min(this.options.ticks.maxTicksLimit ? this.options.ticks.maxTicksLimit : 11,
Math.ceil(this.height / (2 * this.options.ticks.fontSize)));
}
// Make sure we always have at least 2 ticks
@@ -146,6 +156,19 @@
}
}
if (this.options.ticks.suggestedMin) {
this.min = Math.min(this.min, this.options.ticks.suggestedMin);
}
if (this.options.ticks.suggestedMax) {
this.max = Math.max(this.max, this.options.ticks.suggestedMax);
}
if (this.min === this.max) {
this.min--;
this.max++;
}
var niceRange = helpers.niceNum(this.max - this.min, false);
var spacing = helpers.niceNum(niceRange / (maxTicks - 1), true);
var niceMin = Math.floor(this.min / spacing) * spacing;
@@ -182,14 +205,14 @@
},
getLabelForIndex: function(index, datasetIndex) {
return this.getRightValue(this.data.datasets[datasetIndex].data[index]);
return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
},
// Utils
getPixelForValue: function(value, index, datasetIndex, includeOffset) {
// This must be called after fit has been run so that
// this.left, this.top, this.right, and this.bottom have been defined
var rightValue = this.getRightValue(value);
var rightValue = +this.getRightValue(value);
var pixel;
var range = this.end - this.start;
+20 -12
Ver Arquivo
@@ -30,14 +30,18 @@
this.min = null;
this.max = null;
var values = [];
if (this.options.stacked) {
helpers.each(this.data.datasets, function(dataset) {
if (helpers.isDatasetVisible(dataset) && (this.isHorizontal() ? dataset.xAxisID === this.id : dataset.yAxisID === this.id)) {
helpers.each(dataset.data, function(rawValue, index) {
var valuesPerType = {};
var value = this.getRightValue(rawValue);
helpers.each(this.chart.data.datasets, function(dataset) {
if (helpers.isDatasetVisible(dataset) && (this.isHorizontal() ? dataset.xAxisID === this.id : dataset.yAxisID === this.id)) {
if (valuesPerType[dataset.type] === undefined) {
valuesPerType[dataset.type] = [];
}
helpers.each(dataset.data, function(rawValue, index) {
var values = valuesPerType[dataset.type];
var value = +this.getRightValue(rawValue);
if (isNaN(value)) {
return;
}
@@ -54,14 +58,18 @@
}
}, this);
this.min = helpers.min(values);
this.max = helpers.max(values);
helpers.each(valuesPerType, function(valuesForType) {
var minVal = helpers.min(valuesForType);
var maxVal = helpers.max(valuesForType);
this.min = this.min === null ? minVal : Math.min(this.min, minVal);
this.max = this.max === null ? maxVal : Math.max(this.max, maxVal);
}, this);
} else {
helpers.each(this.data.datasets, function(dataset) {
helpers.each(this.chart.data.datasets, function(dataset) {
if (helpers.isDatasetVisible(dataset) && (this.isHorizontal() ? dataset.xAxisID === this.id : dataset.yAxisID === this.id)) {
helpers.each(dataset.data, function(rawValue, index) {
var value = this.getRightValue(rawValue);
var value = +this.getRightValue(rawValue);
if (isNaN(value)) {
return;
}
@@ -137,7 +145,7 @@
},
// Get the correct tooltip label
getLabelForIndex: function(index, datasetIndex) {
return this.getRightValue(this.data.datasets[datasetIndex].data[index]);
return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
},
getPixelForTick: function(index, includeOffset) {
return this.getPixelForValue(this.tickValues[index], null, null, includeOffset);
@@ -145,7 +153,7 @@
getPixelForValue: function(value, index, datasetIndex, includeOffset) {
var pixel;
var newVal = this.getRightValue(value);
var newVal = +this.getRightValue(value);
var range = helpers.log10(this.end) - helpers.log10(this.start);
if (this.isHorizontal()) {
+20 -13
Ver Arquivo
@@ -14,7 +14,7 @@
position: "chartArea",
angleLines: {
show: true,
display: true,
color: "rgba(0, 0, 0, 0.1)",
lineWidth: 1
},
@@ -51,7 +51,7 @@
var LinearRadialScale = Chart.Scale.extend({
getValueCount: function() {
return this.data.labels.length;
return this.chart.data.labels.length;
},
setDimensions: function() {
// Set the unconstrained dimension before label rotation
@@ -67,10 +67,10 @@
this.min = null;
this.max = null;
helpers.each(this.data.datasets, function(dataset) {
helpers.each(this.chart.data.datasets, function(dataset) {
if (helpers.isDatasetVisible(dataset)) {
helpers.each(dataset.data, function(rawValue, index) {
var value = this.getRightValue(rawValue);
var value = +this.getRightValue(rawValue);
if (isNaN(value)) {
return;
}
@@ -101,7 +101,8 @@
// the axis area. For now, we say that the minimum tick spacing in pixels must be 50
// We also limit the maximum number of ticks to 11 which gives a nice 10 squares on
// the graph
var maxTicks = Math.min(11, Math.ceil(this.drawingArea / (1.5 * this.options.ticks.fontSize)));
var maxTicks = Math.min(this.options.ticks.maxTicksLimit ? this.options.ticks.maxTicksLimit : 11,
Math.ceil(this.drawingArea / (1.5 * this.options.ticks.fontSize)));
maxTicks = Math.max(2, maxTicks); // Make sure we always have at least 2 ticks
// To get a "nice" value for the tick spacing, we will use the appropriately named
@@ -151,6 +152,9 @@
this.zeroLineIndex = this.ticks.indexOf(0);
},
getLabelForIndex: function(index, datasetIndex) {
return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
},
getCircumference: function() {
return ((Math.PI * 2) / this.getValueCount());
},
@@ -206,7 +210,7 @@
for (i = 0; i < this.getValueCount(); i++) {
// 5px to space the text slightly out - similar to what we do in the draw function.
pointPosition = this.getPointPosition(i, largestPossibleRadius);
textWidth = this.ctx.measureText(this.options.ticks.callback(this.data.labels[i])).width + 5;
textWidth = this.ctx.measureText(this.options.ticks.callback(this.chart.data.labels[i])).width + 5;
if (i === 0 || i === this.getValueCount() / 2) {
// If we're at index zero, or exactly the middle, we're at exactly the top/bottom
// of the radar chart, so text will be aligned centrally, so we'll half it and compare
@@ -268,7 +272,10 @@
return index * angleMultiplier - (Math.PI / 2);
},
getDistanceFromCenterForValue: function(value) {
if (value === null) return 0; // null always in center
if (value === null) {
return 0; // null always in center
}
// Take into account half font size + the yPadding of the top value
var scalingFactor = this.drawingArea / (this.max - this.min);
if (this.options.reverse) {
@@ -297,7 +304,7 @@
var yHeight = this.yCenter - yCenterOffset;
// Draw circular lines around the scale
if (this.options.gridLines.show) {
if (this.options.gridLines.display) {
ctx.strokeStyle = this.options.gridLines.color;
ctx.lineWidth = this.options.gridLines.lineWidth;
@@ -323,7 +330,7 @@
}
}
if (this.options.ticks.show) {
if (this.options.ticks.display) {
ctx.font = helpers.fontString(this.options.ticks.fontSize, this.options.ticks.fontStyle, this.options.ticks.fontFamily);
if (this.options.ticks.showLabelBackdrop) {
@@ -350,7 +357,7 @@
ctx.strokeStyle = this.options.angleLines.color;
for (var i = this.getValueCount() - 1; i >= 0; i--) {
if (this.options.angleLines.show) {
if (this.options.angleLines.display) {
var outerPosition = this.getPointPosition(i, this.getDistanceFromCenterForValue(this.options.reverse ? this.min : this.max));
ctx.beginPath();
ctx.moveTo(this.xCenter, this.yCenter);
@@ -363,8 +370,8 @@
ctx.font = helpers.fontString(this.options.pointLabels.fontSize, this.options.pointLabels.fontStyle, this.options.pointLabels.fontFamily);
ctx.fillStyle = this.options.pointLabels.fontColor;
var labelsCount = this.data.labels.length,
halfLabelsCount = this.data.labels.length / 2,
var labelsCount = this.chart.data.labels.length,
halfLabelsCount = this.chart.data.labels.length / 2,
quarterLabelsCount = halfLabelsCount / 2,
upperHalf = (i < quarterLabelsCount || i > labelsCount - quarterLabelsCount),
exactQuarter = (i === quarterLabelsCount || i === labelsCount - quarterLabelsCount);
@@ -387,7 +394,7 @@
ctx.textBaseline = 'top';
}
ctx.fillText(this.data.labels[i], pointLabelPosition.x, pointLabelPosition.y);
ctx.fillText(this.chart.data.labels[i], pointLabelPosition.x, pointLabelPosition.y);
}
}
}
+25 -50
Ver Arquivo
@@ -22,44 +22,6 @@
'quarter',
'year',
],
unit: {
'millisecond': {
display: 'SSS [ms]', // 002 ms
maxStep: 1000,
},
'second': {
display: 'h:mm:ss a', // 11:20:01 AM
maxStep: 60,
},
'minute': {
display: 'h:mm:ss a', // 11:20:01 AM
maxStep: 60,
},
'hour': {
display: 'MMM D, hA', // Sept 4, 5PM
maxStep: 24,
},
'day': {
display: 'll', // Sep 4 2015
maxStep: 7,
},
'week': {
display: 'll', // Week 46, or maybe "[W]WW - YYYY" ?
maxStep: 4.3333,
},
'month': {
display: 'MMM YYYY', // Sept 2015
maxStep: 12,
},
'quarter': {
display: '[Q]Q - YYYY', // Q3
maxStep: 4,
},
'year': {
display: 'YYYY', // 2015
maxStep: false,
},
}
};
var defaultConfig = {
@@ -69,7 +31,20 @@
format: false, // false == date objects or use pattern string from http://momentjs.com/docs/#/parsing/string-format/
unit: false, // false == automatic or override with week, month, year, etc.
round: false, // none, or override with week, month, year, etc.
displayFormat: false, // defaults to unit's corresponding unitFormat below or override using pattern string from http://momentjs.com/docs/#/displaying/format/
displayFormat: false, // DEPRECATED
// defaults to unit's corresponding unitFormat below or override using pattern string from http://momentjs.com/docs/#/displaying/format/
displayFormats: {
'millisecond': 'SSS [ms]',
'second': 'h:mm:ss a', // 11:20:01 AM
'minute': 'h:mm:ss a', // 11:20:01 AM
'hour': 'MMM D, hA', // Sept 4, 5PM
'day': 'll', // Sep 4 2015
'week': 'll', // Week 46, or maybe "[W]WW - YYYY" ?
'month': 'MMM YYYY', // Sept 2015
'quarter': '[Q]Q - YYYY', // Q3
'year': 'YYYY', // 2015
},
},
};
@@ -82,8 +57,8 @@
// Only parse these once. If the dataset does not have data as x,y pairs, we will use
// these
var scaleLabelMoments = [];
if (this.data.labels && this.data.labels.length > 0) {
helpers.each(this.data.labels, function(label, index) {
if (this.chart.data.labels && this.chart.data.labels.length > 0) {
helpers.each(this.chart.data.labels, function(label, index) {
var labelMoment = this.parseTime(label);
if (this.options.time.round) {
labelMoment.startOf(this.options.time.round);
@@ -107,7 +82,7 @@
this.lastTick = null;
}
helpers.each(this.data.datasets, function(dataset, datasetIndex) {
helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
var momentsForDataset = [];
if (typeof dataset.data[0] === 'object') {
@@ -145,7 +120,7 @@
// Set unit override if applicable
if (this.options.time.unit) {
this.tickUnit = this.options.time.unit || 'day';
this.displayFormat = time.unit[this.tickUnit].display;
this.displayFormat = this.options.time.displayFormats[this.tickUnit];
this.tickRange = Math.ceil(this.lastTick.diff(this.firstTick, this.tickUnit, true));
} else {
// Determine the smallest needed unit of the time
@@ -156,7 +131,7 @@
// Start as small as possible
this.tickUnit = 'millisecond';
this.tickRange = Math.ceil(this.lastTick.diff(this.firstTick, this.tickUnit, true) + buffer);
this.displayFormat = time.unit[this.tickUnit].display;
this.displayFormat = this.options.time.displayFormats[this.tickUnit];
// Work our way up to comfort
helpers.each(time.units, function(format) {
@@ -165,7 +140,7 @@
}
this.tickUnit = format;
this.tickRange = Math.ceil(this.lastTick.diff(this.firstTick, this.tickUnit) + buffer);
this.displayFormat = time.unit[format].display;
this.displayFormat = this.options.time.displayFormats[format];
}, this);
}
@@ -174,7 +149,7 @@
this.lastTick.endOf(this.tickUnit);
this.smallestLabelSeparation = this.width;
helpers.each(this.data.datasets, function(dataset, datasetIndex) {
helpers.each(this.chart.data.datasets, function(dataset, datasetIndex) {
for (var i = 1; i < this.labelMoments[datasetIndex].length; i++) {
this.smallestLabelSeparation = Math.min(this.smallestLabelSeparation, this.labelMoments[datasetIndex][i].diff(this.labelMoments[datasetIndex][i - 1], this.tickUnit, true));
}
@@ -192,17 +167,17 @@
},
// Get tooltip label
getLabelForIndex: function(index, datasetIndex) {
var label = this.data.labels && index < this.data.labels.length ? this.data.labels[index] : '';
var label = this.chart.data.labels && index < this.chart.data.labels.length ? this.chart.data.labels[index] : '';
if (typeof this.data.datasets[datasetIndex].data[0] === 'object') {
label = this.getRightValue(this.data.datasets[datasetIndex].data[index]);
if (typeof this.chart.data.datasets[datasetIndex].data[0] === 'object') {
label = this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
}
return label;
},
convertTicksToLabels: function() {
this.ticks = this.ticks.map(function(tick, index, ticks) {
var formattedTick = tick.format(this.options.time.displayFormat ? this.options.time.displayFormat : time.unit[this.tickUnit].display);
var formattedTick = tick.format(this.options.time.displayFormat ? this.options.time.displayFormat : this.options.time.displayFormats[this.tickUnit]);
if (this.options.ticks.userCallback) {
return this.options.ticks.userCallback(formattedTick, index, ticks);
+26 -10
Ver Arquivo
@@ -190,7 +190,9 @@ describe('Bar controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -207,7 +209,9 @@ describe('Bar controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
@@ -262,7 +266,7 @@ describe('Bar controller tests', function() {
expect(bar1._xScale).toBe(chart.scales.firstXScaleID);
expect(bar1._yScale).toBe(chart.scales.firstYScaleID);
expect(bar1._model).toEqual({
x: 103.60000000000001,
x: 113.60000000000001,
y: 194,
label: 'label1',
datasetLabel: 'dataset2',
@@ -279,7 +283,7 @@ describe('Bar controller tests', function() {
expect(bar2._xScale).toBe(chart.scales.firstXScaleID);
expect(bar2._yScale).toBe(chart.scales.firstYScaleID);
expect(bar2._model).toEqual({
x: 141.6,
x: 151.60000000000002,
y: 6,
label: 'label2',
datasetLabel: 'dataset2',
@@ -316,7 +320,9 @@ describe('Bar controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -333,7 +339,9 @@ describe('Bar controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
@@ -399,7 +407,9 @@ describe('Bar controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -416,7 +426,9 @@ describe('Bar controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
@@ -519,7 +531,9 @@ describe('Bar controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -536,7 +550,9 @@ describe('Bar controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
+164 -36
Ver Arquivo
@@ -159,7 +159,9 @@ describe('Line controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -176,7 +178,9 @@ describe('Line controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
@@ -192,7 +196,7 @@ describe('Line controller tests', function() {
chartArea: {
bottom: 200,
left: xScale.left,
right: 200,
right: xScale.left + 200,
top: 0
},
data: data,
@@ -267,13 +271,13 @@ describe('Line controller tests', function() {
tension: 0.1,
// Point
x: 71,
x: 81,
y: 62,
// Control points
controlPointPreviousX: 71,
controlPointPreviousX: 81,
controlPointPreviousY: 62,
controlPointNextX: 76,
controlPointNextX: 86,
controlPointNextY: 57.3,
});
@@ -287,13 +291,13 @@ describe('Line controller tests', function() {
tension: 0.1,
// Point
x: 121,
x: 131,
y: 15,
// Control points
controlPointPreviousX: 117.82889384189087,
controlPointPreviousX: 127.82889384189087,
controlPointPreviousY: 12.04867347661131,
controlPointNextX: 127.92889384189088,
controlPointNextX: 137.92889384189088,
controlPointNextY: 21.44867347661131,
});
@@ -307,13 +311,13 @@ describe('Line controller tests', function() {
tension: 0.1,
// Point
x: 172,
x: 182,
y: 156,
// Control points
controlPointPreviousX: 164.8815225337256,
controlPointPreviousX: 174.8815225337256,
controlPointPreviousY: 143.38408449046415,
controlPointNextX: 174.98152253372558,
controlPointNextX: 184.98152253372558,
controlPointNextY: 161.28408449046415,
});
@@ -327,13 +331,13 @@ describe('Line controller tests', function() {
tension: 0.1,
// Point
x: 222,
x: 232,
y: 194,
// Control points
controlPointPreviousX: 217,
controlPointPreviousX: 227,
controlPointPreviousY: 190.2,
controlPointNextX: 222,
controlPointNextX: 232,
controlPointNextY: 194,
});
@@ -383,13 +387,13 @@ describe('Line controller tests', function() {
tension: 0.2,
// Point
x: 71,
x: 81,
y: 62,
// Control points
controlPointPreviousX: 71,
controlPointPreviousX: 81,
controlPointPreviousY: 62,
controlPointNextX: 81,
controlPointNextX: 91,
controlPointNextY: 52.6,
});
@@ -403,13 +407,13 @@ describe('Line controller tests', function() {
tension: 0.2,
// Point
x: 121,
x: 131,
y: 15,
// Control points
controlPointPreviousX: 114.65778768378175,
controlPointPreviousX: 124.65778768378175,
controlPointPreviousY: 9.097346953222619,
controlPointNextX: 134.85778768378177,
controlPointNextX: 144.85778768378177,
controlPointNextY: 27.897346953222623,
});
@@ -423,13 +427,13 @@ describe('Line controller tests', function() {
tension: 0.2,
// Point
x: 172,
x: 182,
y: 156,
// Control points
controlPointPreviousX: 157.76304506745115,
controlPointPreviousX: 167.76304506745115,
controlPointPreviousY: 130.76816898092827,
controlPointNextX: 177.96304506745116,
controlPointNextX: 187.96304506745116,
controlPointNextY: 166.56816898092828,
});
@@ -443,13 +447,13 @@ describe('Line controller tests', function() {
tension: 0.2,
// Point
x: 222,
x: 232,
y: 194,
// Control points
controlPointPreviousX: 212,
controlPointPreviousX: 222,
controlPointPreviousY: 186.4,
controlPointNextX: 222,
controlPointNextX: 232,
controlPointNextY: 194,
});
@@ -505,17 +509,129 @@ describe('Line controller tests', function() {
tension: 0.15,
// Point
x: 71,
x: 81,
y: 62,
// Control points
controlPointPreviousX: 71,
controlPointPreviousX: 81,
controlPointPreviousY: 62,
controlPointNextX: 78.5,
controlPointNextX: 88.5,
controlPointNextY: 54.95,
});
});
it ('should fall back to the line styles for points', function() {
var data = {
datasets: [{
data: [0, 0],
label: 'dataset2',
xAxisID: 'firstXScaleID',
yAxisID: 'firstYScaleID',
// line styles
backgroundColor: 'rgb(98, 98, 98)',
borderColor: 'rgb(8, 8, 8)',
borderWidth: 0.55,
}],
labels: ['label1', 'label2']
};
var mockContext = window.createMockContext();
var VerticalScaleConstructor = Chart.scaleService.getScaleConstructor('linear');
var verticalScaleConfig = Chart.helpers.clone(Chart.scaleService.getScaleDefaults('linear'));
verticalScaleConfig = Chart.helpers.scaleMerge(verticalScaleConfig, Chart.defaults.line.scales.yAxes[0]);
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
chart: {
data: data
},
id: 'firstYScaleID'
});
// Update ticks & set physical dimensions
var verticalSize = yScale.update(50, 200);
yScale.top = 0;
yScale.left = 0;
yScale.right = verticalSize.width;
yScale.bottom = verticalSize.height;
var HorizontalScaleConstructor = Chart.scaleService.getScaleConstructor('category');
var horizontalScaleConfig = Chart.helpers.clone(Chart.scaleService.getScaleDefaults('category'));
horizontalScaleConfig = Chart.helpers.scaleMerge(horizontalScaleConfig, Chart.defaults.line.scales.xAxes[0]);
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
chart: {
data: data
},
id: 'firstXScaleID'
});
// Update ticks & set physical dimensions
var horizontalSize = xScale.update(200, 50);
xScale.left = yScale.right;
xScale.top = yScale.bottom;
xScale.right = horizontalSize.width + xScale.left;
xScale.bottom = horizontalSize.height + xScale.top;
var chart = {
chartArea: {
bottom: 200,
left: xScale.left,
right: 200,
top: 0
},
data: data,
config: {
type: 'line'
},
options: {
elements: {
line: {
backgroundColor: 'rgb(255, 0, 0)',
borderCapStyle: 'round',
borderColor: 'rgb(0, 255, 0)',
borderDash: [],
borderDashOffset: 0.1,
borderJoinStyle: 'bevel',
borderWidth: 1.2,
fill: true,
tension: 0.1,
},
point: {
backgroundColor: Chart.defaults.global.defaultColor,
borderWidth: 1,
borderColor: Chart.defaults.global.defaultColor,
hitRadius: 1,
hoverRadius: 4,
hoverBorderWidth: 1,
radius: 3,
}
},
scales: {
xAxes: [{
id: 'firstXScaleID'
}],
yAxes: [{
id: 'firstYScaleID'
}]
}
},
scales: {
firstXScaleID: xScale,
firstYScaleID: yScale,
}
};
var controller = new Chart.controllers.line(chart, 0);
controller.update();
expect(chart.data.datasets[0].metaData[0]._model.backgroundColor).toBe('rgb(98, 98, 98)');
expect(chart.data.datasets[0].metaData[0]._model.borderColor).toBe('rgb(8, 8, 8)');
expect(chart.data.datasets[0].metaData[0]._model.borderWidth).toBe(0.55);
});
it('should handle number of data point changes in update', function() {
var data = {
datasets: [{
@@ -534,7 +650,9 @@ describe('Line controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -551,7 +669,9 @@ describe('Line controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
@@ -649,7 +769,9 @@ describe('Line controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -666,7 +788,9 @@ describe('Line controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
@@ -783,7 +907,9 @@ describe('Line controller tests', function() {
var yScale = new VerticalScaleConstructor({
ctx: mockContext,
options: verticalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstYScaleID'
});
@@ -800,7 +926,9 @@ describe('Line controller tests', function() {
var xScale = new HorizontalScaleConstructor({
ctx: mockContext,
options: horizontalScaleConfig,
data: data,
chart: {
data: data
},
id: 'firstXScaleID'
});
+7 -7
Ver Arquivo
@@ -219,7 +219,7 @@ describe('Core helper tests', function() {
drawTicks: true, // draw ticks extending towards the label
lineWidth: 1,
offsetGridLines: false,
show: true,
display: true,
zeroLineColor: "rgba(0,0,0,0.25)",
zeroLineWidth: 1,
},
@@ -230,7 +230,7 @@ describe('Core helper tests', function() {
fontSize: 12,
fontStyle: 'normal',
labelString: '',
show: false,
display: false,
},
ticks: {
beginAtZero: false,
@@ -243,7 +243,7 @@ describe('Core helper tests', function() {
mirror: false,
padding: 10,
reverse: false,
show: true,
display: true,
callback: merged.scales.yAxes[1].ticks.callback, // make it nicer, then check explicitly below
},
type: 'linear'
@@ -256,7 +256,7 @@ describe('Core helper tests', function() {
drawTicks: true, // draw ticks extending towards the label
lineWidth: 1,
offsetGridLines: false,
show: true,
display: true,
zeroLineColor: "rgba(0,0,0,0.25)",
zeroLineWidth: 1,
},
@@ -267,7 +267,7 @@ describe('Core helper tests', function() {
fontSize: 12,
fontStyle: 'normal',
labelString: '',
show: false,
display: false,
},
ticks: {
beginAtZero: false,
@@ -280,7 +280,7 @@ describe('Core helper tests', function() {
mirror: false,
padding: 10,
reverse: false,
show: true,
display: true,
callback: merged.scales.yAxes[2].ticks.callback, // make it nicer, then check explicitly below
},
type: 'linear'
@@ -324,7 +324,7 @@ describe('Core helper tests', function() {
it('should do a log10 operation', function() {
expect(helpers.log10(0)).toBe(-Infinity);
expect(helpers.log10(1)).toBe(0);
expect(helpers.log10(1000)).toBe(3);
expect(helpers.log10(1000)).toBeCloseTo(3, 1e-9);
});
it('Should generate ids', function() {
+47 -31
Ver Arquivo
@@ -21,7 +21,9 @@ describe('Test the scale service', function() {
var xScale = new XConstructor({
ctx: mockContext,
options: xScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: xScaleID
});
@@ -30,7 +32,9 @@ describe('Test the scale service', function() {
var yScale = new YConstructor({
ctx: mockContext,
options: yScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: yScaleID
});
@@ -42,24 +46,24 @@ describe('Test the scale service', function() {
Chart.scaleService.update(chartInstance, canvasWidth, canvasHeight);
expect(chartInstance.chartArea).toEqual({
left: 45,
left: 55,
right: 245,
top: 5,
bottom: 76.0423977855504,
bottom: 75.0664716027288,
});
// Is xScale at the right spot
expect(xScale.left).toBe(45);
expect(xScale.left).toBe(55);
expect(xScale.right).toBe(245);
expect(xScale.top).toBe(76.0423977855504);
expect(xScale.top).toBe(75.0664716027288);
expect(xScale.bottom).toBe(145);
expect(xScale.labelRotation).toBe(55);
expect(xScale.labelRotation).toBe(57);
// Is yScale at the right spot
expect(yScale.left).toBe(5);
expect(yScale.right).toBe(45);
expect(yScale.right).toBe(55);
expect(yScale.top).toBe(5);
expect(yScale.bottom).toBe(76.0423977855504);
expect(yScale.bottom).toBe(75.0664716027288);
});
it('should fit scales that are in the top and right positions', function() {
@@ -84,7 +88,9 @@ describe('Test the scale service', function() {
var xScale = new XConstructor({
ctx: mockContext,
options: xScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: xScaleID
});
@@ -94,7 +100,9 @@ describe('Test the scale service', function() {
var yScale = new YConstructor({
ctx: mockContext,
options: yScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: yScaleID
});
@@ -107,22 +115,22 @@ describe('Test the scale service', function() {
expect(chartInstance.chartArea).toEqual({
left: 5,
right: 205,
top: 73.9576022144496,
right: 195,
top: 74.9335283972712,
bottom: 145,
});
// Is xScale at the right spot
expect(xScale.left).toBe(5);
expect(xScale.right).toBe(205);
expect(xScale.right).toBe(195);
expect(xScale.top).toBe(5);
expect(xScale.bottom).toBe(73.9576022144496);
expect(xScale.labelRotation).toBe(55);
expect(xScale.bottom).toBe(74.9335283972712);
expect(xScale.labelRotation).toBe(57);
// Is yScale at the right spot
expect(yScale.left).toBe(205);
expect(yScale.left).toBe(195);
expect(yScale.right).toBe(245);
expect(yScale.top).toBe(73.9576022144496);
expect(yScale.top).toBe(74.9335283972712);
expect(yScale.bottom).toBe(145);
});
@@ -151,7 +159,9 @@ describe('Test the scale service', function() {
var xScale = new XConstructor({
ctx: mockContext,
options: xScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: xScaleID
});
@@ -160,13 +170,17 @@ describe('Test the scale service', function() {
var yScale1 = new YConstructor({
ctx: mockContext,
options: yScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: yScaleID1
});
var yScale2 = new YConstructor({
ctx: mockContext,
options: yScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: yScaleID2
});
@@ -179,28 +193,28 @@ describe('Test the scale service', function() {
Chart.scaleService.update(chartInstance, canvasWidth, canvasHeight);
expect(chartInstance.chartArea).toEqual({
left: 95,
left: 115,
right: 245,
top: 5,
bottom: 70.01536896070459,
bottom: 68.48521368620018,
});
// Is xScale at the right spot
expect(xScale.left).toBe(95);
expect(xScale.left).toBe(115);
expect(xScale.right).toBe(245);
expect(xScale.top).toBe(70.01536896070459);
expect(xScale.top).toBe(68.48521368620018);
expect(xScale.bottom).toBe(145);
// Are yScales at the right spot
expect(yScale1.left).toBe(5);
expect(yScale1.right).toBe(45);
expect(yScale1.right).toBe(55);
expect(yScale1.top).toBe(5);
expect(yScale1.bottom).toBe(70.01536896070459);
expect(yScale1.bottom).toBe(68.48521368620018);
expect(yScale2.left).toBe(45);
expect(yScale2.right).toBe(95);
expect(yScale2.left).toBe(55);
expect(yScale2.right).toBe(115);
expect(yScale2.top).toBe(5);
expect(yScale2.bottom).toBe(70.01536896070459);
expect(yScale2.bottom).toBe(68.48521368620018);
});
// This is an oddball case. What happens is, when the scales are fit the first time they must fit within the assigned size. In this case,
@@ -230,7 +244,9 @@ describe('Test the scale service', function() {
var scale = new ScaleConstructor({
ctx: mockContext,
options: scaleConfig,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
+609 -121
Ver Arquivo
@@ -22,6 +22,8 @@ describe('Line element tests', function() {
_view: {
x: 0,
y: 10,
controlPointNextX: 0,
controlPointNextY: 10
}
}));
points.push(new Chart.elements.Point({
@@ -30,6 +32,10 @@ describe('Line element tests', function() {
_view: {
x: 5,
y: 0,
controlPointPreviousX: 5,
controlPointPreviousY: 0,
controlPointNextX: 5,
controlPointNextY: 0
}
}));
points.push(new Chart.elements.Point({
@@ -38,6 +44,10 @@ describe('Line element tests', function() {
_view: {
x: 15,
y: -10,
controlPointPreviousX: 15,
controlPointPreviousY: -10,
controlPointNextX: 15,
controlPointNextY: -10
}
}));
points.push(new Chart.elements.Point({
@@ -46,6 +56,10 @@ describe('Line element tests', function() {
_view: {
x: 19,
y: -5,
controlPointPreviousX: 19,
controlPointPreviousY: -5,
controlPointNextX: 19,
controlPointNextY: -5
}
}));
@@ -68,21 +82,6 @@ describe('Line element tests', function() {
expect(mockContext.getCalls()).toEqual([{
name: 'save',
args: [],
}, {
name: 'moveTo',
args: [0, 0]
}, {
name: 'lineTo',
args: [0, 10]
}, {
name: 'lineTo',
args: [5, 0]
}, {
name: 'lineTo',
args: [15, -10]
}, {
name: 'lineTo',
args: [19, -5]
}, {
name: 'setLineCap',
args: ['butt']
@@ -108,19 +107,16 @@ describe('Line element tests', function() {
args: []
}, {
name: 'moveTo',
args: [0, 0]
}, {
name: 'lineTo',
args: [0, 10]
}, {
name: 'lineTo',
args: [5, 0]
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'lineTo',
args: [15, -10]
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'lineTo',
args: [19, -5]
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'stroke',
args: [],
@@ -140,7 +136,9 @@ describe('Line element tests', function() {
_index: 0,
_view: {
x: 0,
y: 10
y: 10,
controlPointNextX: 0,
controlPointNextY: 10
}
}));
points.push(new Chart.elements.Point({
@@ -148,7 +146,11 @@ describe('Line element tests', function() {
_index: 1,
_view: {
x: 5,
y: 0
y: 0,
controlPointPreviousX: 5,
controlPointPreviousY: 0,
controlPointNextX: 5,
controlPointNextY: 0
}
}));
points.push(new Chart.elements.Point({
@@ -156,7 +158,11 @@ describe('Line element tests', function() {
_index: 2,
_view: {
x: 15,
y: -10
y: -10,
controlPointPreviousX: 15,
controlPointPreviousY: -10,
controlPointNextX: 15,
controlPointNextY: -10
}
}));
points.push(new Chart.elements.Point({
@@ -164,7 +170,11 @@ describe('Line element tests', function() {
_index: 3,
_view: {
x: 19,
y: -5
y: -5,
controlPointPreviousX: 19,
controlPointPreviousY: -5,
controlPointNextX: 19,
controlPointNextY: -5
}
}));
@@ -195,6 +205,9 @@ describe('Line element tests', function() {
var expected = [{
name: 'save',
args: [],
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 2]
@@ -202,14 +215,14 @@ describe('Line element tests', function() {
name: 'lineTo',
args: [0, 10]
}, {
name: 'lineTo',
args: [5, 0]
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'lineTo',
args: [15, -10]
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'lineTo',
args: [19, -5]
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'lineTo',
args: [19, 2]
@@ -248,6 +261,103 @@ describe('Line element tests', function() {
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 10]
}, {
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'stroke',
args: [],
}, {
name: 'restore',
args: []
}];
expect(mockContext.getCalls()).toEqual(expected);
});
it ('should skip points correctly', function() {
var mockContext = window.createMockContext();
// Create our points
var points = [];
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 0,
_view: {
x: 0,
y: 10,
controlPointNextX: 0,
controlPointNextY: 10
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 1,
_view: {
x: 5,
y: 0,
controlPointPreviousX: 5,
controlPointPreviousY: 0,
controlPointNextX: 5,
controlPointNextY: 0
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 2,
_view: {
x: 15,
y: -10,
controlPointPreviousX: 15,
controlPointPreviousY: -10,
controlPointNextX: 15,
controlPointNextY: -10,
skip: true
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 3,
_view: {
x: 19,
y: -5,
controlPointPreviousX: 19,
controlPointPreviousY: -5,
controlPointNextX: 19,
controlPointNextY: -5
}
}));
var line = new Chart.elements.Line({
_datasetindex: 2,
_chart: {
ctx: mockContext,
},
_children: points,
// Need to provide some settings
_view: {
fill: true,
scaleZero: 2, // for filling lines
tension: 0.0, // no bezier curve for now
}
});
line.draw();
var expected = [{
name: 'save',
args: []
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 2]
@@ -255,14 +365,67 @@ describe('Line element tests', function() {
name: 'lineTo',
args: [0, 10]
}, {
name: 'lineTo',
args: [5, 0]
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'lineTo',
args: [5, 2]
}, {
name: 'moveTo',
args: [19, 2]
}, {
name: 'lineTo',
args: [19, -5]
}, {
name: 'lineTo',
args: [19, 2]
}, {
name: 'lineTo',
args: [15, -10]
args: [0, 2]
}, {
name: 'lineTo',
args: [19, -5]
name: 'setFillStyle',
args: ['rgba(0,0,0,0.1)']
}, {
name: 'closePath',
args: []
}, {
name: 'fill',
args: []
}, {
name: 'setLineCap',
args: ['butt']
}, {
name: 'setLineDash',
args: [
[]
]
}, {
name: 'setLineDashOffset',
args: [0.0]
}, {
name: 'setLineJoin',
args: ['miter']
}, {
name: 'setLineWidth',
args: [3]
}, {
name: 'setStrokeStyle',
args: ['rgba(0,0,0,0.1)']
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 10]
}, {
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'moveTo',
args: [19, -5]
}, {
name: 'moveTo',
args: [19, -5]
}, {
name: 'stroke',
args: [],
@@ -283,7 +446,11 @@ describe('Line element tests', function() {
_index: 0,
_view: {
x: 0,
y: 10
y: 10,
controlPointPreviousX: 0,
controlPointPreviousY: 10,
controlPointNextX: 0,
controlPointNextY: 10
}
}));
points.push(new Chart.elements.Point({
@@ -291,7 +458,11 @@ describe('Line element tests', function() {
_index: 1,
_view: {
x: 5,
y: 0
y: 0,
controlPointPreviousX: 5,
controlPointPreviousY: 0,
controlPointNextX: 5,
controlPointNextY: 0
}
}));
points.push(new Chart.elements.Point({
@@ -299,7 +470,11 @@ describe('Line element tests', function() {
_index: 2,
_view: {
x: 15,
y: -10
y: -10,
controlPointPreviousX: 15,
controlPointPreviousY: -10,
controlPointNextX: 15,
controlPointNextY: -10
}
}));
points.push(new Chart.elements.Point({
@@ -307,7 +482,11 @@ describe('Line element tests', function() {
_index: 3,
_view: {
x: 19,
y: -5
y: -5,
controlPointPreviousX: 19,
controlPointPreviousY: -5,
controlPointNextX: 19,
controlPointNextY: -5
}
}));
@@ -320,9 +499,12 @@ describe('Line element tests', function() {
_loop: true, // want the line to loop back to the first point
// Need to provide some settings
_view: {
fill: false, // don't want to fill
fill: true, // don't want to fill
tension: 0.0, // no bezier curve for now
scaleZero: 0,
scaleZero: {
x: 3,
y: 2
},
}
});
@@ -331,24 +513,36 @@ describe('Line element tests', function() {
expect(mockContext.getCalls()).toEqual([{
name: 'save',
args: [],
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 0]
args: [3, 2]
}, {
name: 'lineTo',
args: [0, 10]
}, {
name: 'lineTo',
args: [5, 0]
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'lineTo',
args: [15, -10]
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'lineTo',
args: [19, -5]
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'lineTo',
args: [0, 10]
name: 'bezierCurveTo',
args: [19, -5, 0, 10, 0, 10]
}, {
name: 'setFillStyle',
args: ['rgba(0,0,0,0.1)']
}, {
name: 'closePath',
args: []
}, {
name: 'fill',
args: []
}, {
name: 'setLineCap',
args: ['butt']
@@ -374,22 +568,19 @@ describe('Line element tests', function() {
args: []
}, {
name: 'moveTo',
args: [0, 0]
}, {
name: 'lineTo',
args: [0, 10]
}, {
name: 'lineTo',
args: [5, 0]
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'lineTo',
args: [15, -10]
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'lineTo',
args: [19, -5]
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'lineTo',
args: [0, 10]
name: 'bezierCurveTo',
args: [19, -5, 0, 10, 0, 10]
}, {
name: 'stroke',
args: [],
@@ -399,7 +590,7 @@ describe('Line element tests', function() {
}]);
});
it('should draw with bezier curves if tension > 0', function() {
it('should be able to draw with a loop back to the beginning point when there is a skip in the middle of the dataset', function() {
var mockContext = window.createMockContext();
// Create our points
@@ -410,10 +601,10 @@ describe('Line element tests', function() {
_view: {
x: 0,
y: 10,
controlPointNextX: 1,
controlPointNextY: 1,
controlPointPreviousX: 0,
controlPointPreviousY: 0,
controlPointPreviousY: 10,
controlPointNextX: 0,
controlPointNextY: 10
}
}));
points.push(new Chart.elements.Point({
@@ -422,10 +613,11 @@ describe('Line element tests', function() {
_view: {
x: 5,
y: 0,
controlPointNextX: 6,
controlPointNextY: 7,
controlPointPreviousX: 4,
controlPointPreviousY: 3,
controlPointPreviousX: 5,
controlPointPreviousY: 0,
controlPointNextX: 5,
controlPointNextY: 0,
skip: true
}
}));
points.push(new Chart.elements.Point({
@@ -434,10 +626,10 @@ describe('Line element tests', function() {
_view: {
x: 15,
y: -10,
controlPointNextX: 16,
controlPointNextY: 17,
controlPointPreviousX: 14,
controlPointPreviousY: 13,
controlPointPreviousX: 15,
controlPointPreviousY: -10,
controlPointNextX: 15,
controlPointNextY: -10
}
}));
points.push(new Chart.elements.Point({
@@ -446,10 +638,10 @@ describe('Line element tests', function() {
_view: {
x: 19,
y: -5,
controlPointNextX: 20,
controlPointNextY: 21,
controlPointPreviousX: 18,
controlPointPreviousY: 17,
controlPointPreviousX: 19,
controlPointPreviousY: -5,
controlPointNextX: 19,
controlPointNextY: -5
}
}));
@@ -459,51 +651,47 @@ describe('Line element tests', function() {
ctx: mockContext,
},
_children: points,
_loop: true, // want the line to loop back to the first point
// Need to provide some settings
_view: {
fill: true,
scaleZero: 2, // for filling lines
tension: 0.5, // have bezier curves
borderCapStyle: 'round',
borderColor: 'rgb(255, 255, 0)',
borderDash: [2, 2],
borderDashOffset: 1.5,
borderJoinStyle: 'bevel',
borderWidth: 4,
backgroundColor: 'rgb(0, 0, 0)'
fill: true, // don't want to fill
tension: 0.0, // no bezier curve for now
scaleZero: {
x: 3,
y: 2
},
}
});
line.draw();
var expected = [{
expect(mockContext.getCalls()).toEqual([{
name: 'save',
args: [],
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 2]
args: [3, 2]
}, {
name: 'lineTo',
args: [0, 10]
}, {
name: 'bezierCurveTo',
args: [1, 1, 4, 3, 5, 0]
}, {
name: 'bezierCurveTo',
args: [6, 7, 14, 13, 15, -10]
}, {
name: 'bezierCurveTo',
args: [16, 17, 18, 17, 19, -5]
name: 'lineTo',
args: [3, 2]
}, {
name: 'lineTo',
args: [19, 2]
args: [15, -10]
}, {
name: 'lineTo',
args: [0, 2]
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'bezierCurveTo',
args: [19, -5, 0, 10, 0, 10]
}, {
name: 'setFillStyle',
args: ['rgb(0, 0, 0)']
args: ['rgba(0,0,0,0.1)']
}, {
name: 'closePath',
args: []
@@ -512,49 +700,349 @@ describe('Line element tests', function() {
args: []
}, {
name: 'setLineCap',
args: ['round']
args: ['butt']
}, {
name: 'setLineDash',
args: [
[2, 2]
[]
]
}, {
name: 'setLineDashOffset',
args: [1.5]
args: [0.0]
}, {
name: 'setLineJoin',
args: ['bevel']
args: ['miter']
}, {
name: 'setLineWidth',
args: [4]
args: [3]
}, {
name: 'setStrokeStyle',
args: ['rgb(255, 255, 0)']
args: ['rgba(0,0,0,0.1)']
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 2]
}, {
name: 'lineTo',
args: [0, 10]
}, {
name: 'bezierCurveTo',
args: [1, 1, 4, 3, 5, 0]
name: 'moveTo',
args: [15, -10]
}, {
name: 'moveTo',
args: [15, -10]
}, {
name: 'bezierCurveTo',
args: [6, 7, 14, 13, 15, -10]
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'bezierCurveTo',
args: [16, 17, 18, 17, 19, -5]
args: [19, -5, 0, 10, 0, 10]
}, {
name: 'stroke',
args: [],
}, {
name: 'restore',
args: []
}];
expect(mockContext.getCalls()).toEqual(expected);
}]);
});
it('should be able to draw with a loop back to the beginning point when the first point is skipped', function() {
var mockContext = window.createMockContext();
// Create our points
var points = [];
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 0,
_view: {
x: 0,
y: 10,
controlPointPreviousX: 0,
controlPointPreviousY: 10,
controlPointNextX: 0,
controlPointNextY: 10,
skip: true
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 1,
_view: {
x: 5,
y: 0,
controlPointPreviousX: 5,
controlPointPreviousY: 0,
controlPointNextX: 5,
controlPointNextY: 0,
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 2,
_view: {
x: 15,
y: -10,
controlPointPreviousX: 15,
controlPointPreviousY: -10,
controlPointNextX: 15,
controlPointNextY: -10
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 3,
_view: {
x: 19,
y: -5,
controlPointPreviousX: 19,
controlPointPreviousY: -5,
controlPointNextX: 19,
controlPointNextY: -5
}
}));
var line = new Chart.elements.Line({
_datasetindex: 2,
_chart: {
ctx: mockContext,
},
_children: points,
_loop: true, // want the line to loop back to the first point
// Need to provide some settings
_view: {
fill: true, // don't want to fill
tension: 0.0, // no bezier curve for now
scaleZero: {
x: 3,
y: 2
},
}
});
line.draw();
expect(mockContext.getCalls()).toEqual([{
name: 'save',
args: [],
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [3, 2]
}, {
name: 'lineTo',
args: [5, 0]
}, {
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'lineTo',
args: [3, 2]
}, {
name: 'setFillStyle',
args: ['rgba(0,0,0,0.1)']
}, {
name: 'closePath',
args: []
}, {
name: 'fill',
args: []
}, {
name: 'setLineCap',
args: ['butt']
}, {
name: 'setLineDash',
args: [
[]
]
}, {
name: 'setLineDashOffset',
args: [0.0]
}, {
name: 'setLineJoin',
args: ['miter']
}, {
name: 'setLineWidth',
args: [3]
}, {
name: 'setStrokeStyle',
args: ['rgba(0,0,0,0.1)']
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 10]
}, {
name: 'moveTo',
args: [5, 0]
}, {
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'bezierCurveTo',
args: [15, -10, 19, -5, 19, -5]
}, {
name: 'stroke',
args: [],
}, {
name: 'restore',
args: []
}]);
});
it('should be able to draw with a loop back to the beginning point when the last point is skipped', function() {
var mockContext = window.createMockContext();
// Create our points
var points = [];
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 0,
_view: {
x: 0,
y: 10,
controlPointPreviousX: 0,
controlPointPreviousY: 10,
controlPointNextX: 0,
controlPointNextY: 10
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 1,
_view: {
x: 5,
y: 0,
controlPointPreviousX: 5,
controlPointPreviousY: 0,
controlPointNextX: 5,
controlPointNextY: 0,
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 2,
_view: {
x: 15,
y: -10,
controlPointPreviousX: 15,
controlPointPreviousY: -10,
controlPointNextX: 15,
controlPointNextY: -10
}
}));
points.push(new Chart.elements.Point({
_datasetindex: 2,
_index: 3,
_view: {
x: 19,
y: -5,
controlPointPreviousX: 19,
controlPointPreviousY: -5,
controlPointNextX: 19,
controlPointNextY: -5,
skip: true
}
}));
var line = new Chart.elements.Line({
_datasetindex: 2,
_chart: {
ctx: mockContext,
},
_children: points,
_loop: true, // want the line to loop back to the first point
// Need to provide some settings
_view: {
fill: true, // don't want to fill
tension: 0.0, // no bezier curve for now
scaleZero: {
x: 3,
y: 2
},
}
});
line.draw();
expect(mockContext.getCalls()).toEqual([{
name: 'save',
args: [],
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [3, 2]
}, {
name: 'lineTo',
args: [0, 10]
}, {
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'lineTo',
args: [3, 2]
}, {
name: 'lineTo',
args: [3, 2]
}, {
name: 'setFillStyle',
args: ['rgba(0,0,0,0.1)']
}, {
name: 'closePath',
args: []
}, {
name: 'fill',
args: []
}, {
name: 'setLineCap',
args: ['butt']
}, {
name: 'setLineDash',
args: [
[]
]
}, {
name: 'setLineDashOffset',
args: [0.0]
}, {
name: 'setLineJoin',
args: ['miter']
}, {
name: 'setLineWidth',
args: [3]
}, {
name: 'setStrokeStyle',
args: ['rgba(0,0,0,0.1)']
}, {
name: 'beginPath',
args: []
}, {
name: 'moveTo',
args: [0, 10]
}, {
name: 'bezierCurveTo',
args: [0, 10, 5, 0, 5, 0]
}, {
name: 'bezierCurveTo',
args: [5, 0, 15, -10, 15, -10]
}, {
name: 'moveTo',
args: [19, -5]
}, {
name: 'stroke',
args: [],
}, {
name: 'restore',
args: []
}]);
});
});
+12 -6
Ver Arquivo
@@ -18,7 +18,7 @@ describe('Category scale tests', function() {
drawTicks: true, // draw ticks extending towards the label
lineWidth: 1,
offsetGridLines: false,
show: true,
display: true,
zeroLineColor: "rgba(0,0,0,0.25)",
zeroLineWidth: 1,
},
@@ -29,7 +29,7 @@ describe('Category scale tests', function() {
fontSize: 12,
fontStyle: 'normal',
labelString: '',
show: false,
display: false,
},
ticks: {
beginAtZero: false,
@@ -42,7 +42,7 @@ describe('Category scale tests', function() {
mirror: false,
padding: 10,
reverse: false,
show: true,
display: true,
callback: defaultConfig.ticks.callback, // make this nicer, then check explicitly below
}
});
@@ -67,7 +67,9 @@ describe('Category scale tests', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -93,7 +95,9 @@ describe('Category scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -151,7 +155,9 @@ describe('Category scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
+393 -35
Ver Arquivo
@@ -17,7 +17,7 @@ describe('Linear Scale', function() {
drawTicks: true, // draw ticks extending towards the label
lineWidth: 1,
offsetGridLines: false,
show: true,
display: true,
zeroLineColor: "rgba(0,0,0,0.25)",
zeroLineWidth: 1,
},
@@ -28,7 +28,7 @@ describe('Linear Scale', function() {
fontSize: 12,
fontStyle: 'normal',
labelString: '',
show: false,
display: false,
},
ticks: {
beginAtZero: false,
@@ -41,7 +41,7 @@ describe('Linear Scale', function() {
mirror: false,
padding: 10,
reverse: false,
show: true,
display: true,
callback: defaultConfig.ticks.callback, // make this work nicer, then check below
}
});
@@ -69,7 +69,48 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: Chart.scaleService.getScaleDefaults('linear'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
expect(scale).not.toEqual(undefined); // must construct
expect(scale.min).toBe(undefined); // not yet set
expect(scale.max).toBe(undefined);
// Set arbitrary width and height for now
scale.width = 50;
scale.height = 400;
scale.buildTicks();
expect(scale.min).toBe(-100);
expect(scale.max).toBe(150);
});
it('Should correctly determine the max & min of string data values', function() {
var scaleID = 'myScale';
var mockData = {
datasets: [{
yAxisID: scaleID,
data: ['10', '5', '0', '-5', '78', '-100']
}, {
yAxisID: 'second scale',
data: ['-1000', '1000'],
}, {
yAxisID: scaleID,
data: ['150']
}]
};
var Constructor = Chart.scaleService.getScaleConstructor('linear');
var scale = new Constructor({
ctx: {},
options: Chart.scaleService.getScaleDefaults('linear'), // use default config for scale
chart: {
data: mockData
},
id: scaleID
});
@@ -107,7 +148,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: Chart.scaleService.getScaleDefaults('linear'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -152,7 +195,9 @@ describe('Linear Scale', function() {
var verticalScale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -169,7 +214,9 @@ describe('Linear Scale', function() {
var horizontalScale = new Constructor({
ctx: {},
options: horizontalConfig,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -188,13 +235,19 @@ describe('Linear Scale', function() {
var mockData = {
datasets: [{
yAxisID: scaleID,
data: [10, 5, 0, -5, 78, -100]
data: [10, 5, 0, -5, 78, -100],
type: 'bar'
}, {
yAxisID: 'second scale',
data: [-1000, 1000],
}, {
yAxisID: scaleID,
data: [150, 0, 0, -100, -10, 9]
data: [150, 0, 0, -100, -10, 9],
type: 'bar'
}, {
yAxisID: scaleID,
data: [10, 10, 10, 10, 10, 10],
type: 'line'
}]
};
@@ -205,7 +258,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -245,7 +300,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -270,7 +327,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -283,6 +342,39 @@ describe('Linear Scale', function() {
expect(scale.max).toBe(1);
});
it('Should use the suggestedMin and suggestedMax options', function() {
var scaleID = 'myScale';
var mockData = {
datasets: [{
yAxisID: scaleID,
data: [1, 1, 1, 2, 1, 0]
}]
};
var config = Chart.helpers.clone(Chart.scaleService.getScaleDefaults('linear'));
config.ticks.suggestedMin = -10;
config.ticks.suggestedMax = 10;
var Constructor = Chart.scaleService.getScaleConstructor('linear');
var scale = new Constructor({
ctx: {},
options: config,
chart: {
data: mockData
},
id: scaleID
});
// Set arbitrary width and height for now
scale.width = 50;
scale.height = 400;
scale.buildTicks();
expect(scale.min).toBe(-10);
expect(scale.max).toBe(10);
});
it('should forcibly include 0 in the range if the beginAtZero option is used', function() {
var scaleID = 'myScale';
@@ -300,7 +392,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -339,7 +433,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -371,7 +467,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -403,7 +501,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -428,7 +528,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -457,7 +559,9 @@ describe('Linear Scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -484,7 +588,9 @@ describe('Linear Scale', function() {
var verticalScale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -510,7 +616,9 @@ describe('Linear Scale', function() {
var horizontalScale = new Constructor({
ctx: mockContext,
options: horizontalConfig,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -549,16 +657,18 @@ describe('Linear Scale', function() {
var verticalScale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
var minSize = verticalScale.update(100, 300);
expect(minSize).toEqual({
width: 30,
width: 40,
height: 300,
});
expect(verticalScale.width).toBe(30);
expect(verticalScale.width).toBe(40);
expect(verticalScale.height).toBe(300);
expect(verticalScale.paddingTop).toBe(6);
expect(verticalScale.paddingBottom).toBe(6);
@@ -582,10 +692,10 @@ describe('Linear Scale', function() {
expect(verticalScale.paddingRight).toBe(0);
// Extra size when scale label showing
config.scaleLabel.show = true;
config.scaleLabel.display = true;
minSize = verticalScale.update(100, 300);
expect(minSize).toEqual({
width: 48,
width: 58,
height: 300,
});
});
@@ -608,7 +718,9 @@ describe('Linear Scale', function() {
var horizontalScale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -642,7 +754,7 @@ describe('Linear Scale', function() {
expect(horizontalScale.paddingRight).toBe(2);
// Extra size when scale label showing
config.scaleLabel.show = true;
config.scaleLabel.display = true;
minSize = horizontalScale.update(200, 300);
expect(minSize).toEqual({
width: 200,
@@ -668,7 +780,9 @@ describe('Linear Scale', function() {
var horizontalScale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -820,8 +934,8 @@ describe('Linear Scale', function() {
// Turn off some drawing
config.gridLines.drawTicks = false;
config.gridLines.drawOnChartArea = false;
config.ticks.show = false;
config.scaleLabel.show = true;
config.ticks.display = false;
config.scaleLabel.display = true;
config.scaleLabel.labelString = 'myLabel';
mockContext.resetCalls();
@@ -899,7 +1013,9 @@ describe('Linear Scale', function() {
var verticalScale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -1319,8 +1435,8 @@ describe('Linear Scale', function() {
// Turn off some drawing
config.gridLines.drawTicks = false;
config.gridLines.drawOnChartArea = false;
config.ticks.show = false;
config.scaleLabel.show = true;
config.ticks.display = false;
config.scaleLabel.display = true;
mockContext.resetCalls();
@@ -1421,7 +1537,7 @@ describe('Linear Scale', function() {
}, {
"name": "rotate",
"args": [-1.5707963267948966]
}, {
}, {
"name": "setFillStyle",
"args": ["#666"]
}, {
@@ -1432,4 +1548,246 @@ describe('Linear Scale', function() {
"args": []
}]);
});
});
it("should not draw lines where the callback function returned null or undefined", function() {
var scaleID = 'myScale';
var mockData = {
datasets: [{
xAxisID: scaleID, // for the horizontal scale
yAxisID: scaleID,
data: [-5, 0, 2, -3, 5]
}]
};
var mockContext = window.createMockContext();
var config = Chart.helpers.clone(Chart.scaleService.getScaleDefaults('linear'));
config.ticks.callback = function(tickValue, index) {
return index % 2 === 0 ? null : tickValue.toString();
};
var Constructor = Chart.scaleService.getScaleConstructor('linear');
var verticalScale = new Constructor({
ctx: mockContext,
options: config,
chart: {
data: mockData
},
id: scaleID
});
var minSize = verticalScale.update(100, 300);
minSize = verticalScale.update(30, 300, {
left: 0,
right: 0,
top: 15,
bottom: 3
});
expect(minSize).toEqual({
width: 30,
height: 300,
});
verticalScale.left = 0;
verticalScale.right = minSize.width;
verticalScale.top = 0;
verticalScale.bottom = minSize.height;
var chartArea = {
top: 0,
bottom: minSize.height,
left: minSize.width,
right: minSize.width + 100
};
mockContext.resetCalls();
verticalScale.draw(chartArea);
expect(mockContext.getCalls()).toEqual([{
"name": "setFillStyle",
"args": ["#666"]
}, {
"name": "setLineWidth",
"args": [1]
}, {
"name": "setStrokeStyle",
"args": ["rgba(0, 0, 0, 0.1)"]
}, {
"name": "beginPath",
"args": []
}, {
"name": "moveTo",
"args": [25, 30.2]
}, {
"name": "lineTo",
"args": [30, 30.2]
}, {
"name": "moveTo",
"args": [30, 30.2]
}, {
"name": "lineTo",
"args": [130, 30.2]
}, {
"name": "stroke",
"args": []
}, {
"name": "save",
"args": []
}, {
"name": "translate",
"args": [20, 29.7]
}, {
"name": "rotate",
"args": [-0]
}, {
"name": "fillText",
"args": ["4", 0, 0]
}, {
"name": "restore",
"args": []
}, {
"name": "beginPath",
"args": []
}, {
"name": "moveTo",
"args": [25, 89.6]
}, {
"name": "lineTo",
"args": [30, 89.6]
}, {
"name": "moveTo",
"args": [30, 89.6]
}, {
"name": "lineTo",
"args": [130, 89.6]
}, {
"name": "stroke",
"args": []
}, {
"name": "save",
"args": []
}, {
"name": "translate",
"args": [20, 89.1]
}, {
"name": "rotate",
"args": [-0]
}, {
"name": "fillText",
"args": ["2", 0, 0]
}, {
"name": "restore",
"args": []
}, {
"name": "setLineWidth",
"args": [1]
}, {
"name": "setStrokeStyle",
"args": ["rgba(0,0,0,0.25)"]
}, {
"name": "beginPath",
"args": []
}, {
"name": "moveTo",
"args": [25, 149]
}, {
"name": "lineTo",
"args": [30, 149]
}, {
"name": "moveTo",
"args": [30, 149]
}, {
"name": "lineTo",
"args": [130, 149]
}, {
"name": "stroke",
"args": []
}, {
"name": "save",
"args": []
}, {
"name": "translate",
"args": [20, 148.5]
}, {
"name": "rotate",
"args": [-0]
}, {
"name": "fillText",
"args": ["0", 0, 0]
}, {
"name": "restore",
"args": []
}, {
"name": "setLineWidth",
"args": [1]
}, {
"name": "setStrokeStyle",
"args": ["rgba(0, 0, 0, 0.1)"]
}, {
"name": "beginPath",
"args": []
}, {
"name": "moveTo",
"args": [25, 208.4]
}, {
"name": "lineTo",
"args": [30, 208.4]
}, {
"name": "moveTo",
"args": [30, 208.4]
}, {
"name": "lineTo",
"args": [130, 208.4]
}, {
"name": "stroke",
"args": []
}, {
"name": "save",
"args": []
}, {
"name": "translate",
"args": [20, 207.9]
}, {
"name": "rotate",
"args": [-0]
}, {
"name": "fillText",
"args": ["-2", 0, 0]
}, {
"name": "restore",
"args": []
}, {
"name": "beginPath",
"args": []
}, {
"name": "moveTo",
"args": [25, 267.8]
}, {
"name": "lineTo",
"args": [30, 267.8]
}, {
"name": "moveTo",
"args": [30, 267.8]
}, {
"name": "lineTo",
"args": [130, 267.8]
}, {
"name": "stroke",
"args": []
}, {
"name": "save",
"args": []
}, {
"name": "translate",
"args": [20, 267.3]
}, {
"name": "rotate",
"args": [-0]
}, {
"name": "fillText",
"args": ["-4", 0, 0]
}, {
"name": "restore",
"args": []
}])
});
});
+93 -21
Ver Arquivo
@@ -16,7 +16,7 @@ describe('Logarithmic Scale tests', function() {
drawTicks: true,
lineWidth: 1,
offsetGridLines: false,
show: true,
display: true,
zeroLineColor: "rgba(0,0,0,0.25)",
zeroLineWidth: 1,
},
@@ -27,7 +27,7 @@ describe('Logarithmic Scale tests', function() {
fontSize: 12,
fontStyle: 'normal',
labelString: '',
show: false,
display: false,
},
ticks: {
beginAtZero: false,
@@ -40,7 +40,7 @@ describe('Logarithmic Scale tests', function() {
mirror: false,
padding: 10,
reverse: false,
show: true,
display: true,
callback: defaultConfig.ticks.callback, // make this nicer, then check explicitly below
},
});
@@ -70,7 +70,45 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('logarithmic'), // use default config for scale
data: mockData,
chart: {
data: mockData,
},
id: scaleID
});
expect(scale).not.toEqual(undefined); // must construct
expect(scale.min).toBe(undefined); // not yet set
expect(scale.max).toBe(undefined);
scale.update(400, 400);
expect(scale.min).toBe(1);
expect(scale.max).toBe(10000);
});
it('Should correctly determine the max & min of string data values', function() {
var scaleID = 'myScale';
var mockData = {
datasets: [{
yAxisID: scaleID,
data: ['10', '5', '5000', '78', '450']
}, {
yAxisID: 'second scale',
data: ['1', '1000', '10', '100'],
}, {
yAxisID: scaleID,
data: ['150']
}]
};
var mockContext = window.createMockContext();
var Constructor = Chart.scaleService.getScaleConstructor('logarithmic');
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('logarithmic'), // use default config for scale
chart: {
data: mockData,
},
id: scaleID
});
@@ -105,7 +143,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('logarithmic'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -147,7 +187,9 @@ describe('Logarithmic Scale tests', function() {
var verticalScale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -160,7 +202,9 @@ describe('Logarithmic Scale tests', function() {
var horizontalScale = new Constructor({
ctx: mockContext,
options: horizontalConfig,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -175,13 +219,19 @@ describe('Logarithmic Scale tests', function() {
var mockData = {
datasets: [{
yAxisID: scaleID,
data: [10, 5, 1, 5, 78, 100]
data: [10, 5, 1, 5, 78, 100],
type: 'bar'
}, {
yAxisID: 'second scale',
data: [-1000, 1000],
}, {
yAxisID: scaleID,
data: [150, 10, 10, 100, 10, 9]
data: [150, 10, 10, 100, 10, 9],
type: 'bar'
}, {
yAxisID: scaleID,
data: [100, 100, 100, 100, 100, 100],
type: 'line'
}]
};
@@ -193,7 +243,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -208,17 +260,21 @@ describe('Logarithmic Scale tests', function() {
var mockData = {
datasets: [{
yAxisID: scaleID,
data: [10, 5, 1, 5, 78, 100]
data: [10, 5, 1, 5, 78, 100],
type: 'bar'
}, {
yAxisID: 'second scale',
data: [-1000, 1000],
type: 'bar'
}, {
yAxisID: scaleID,
data: [150, 10, 10, 100, 10, 9]
data: [150, 10, 10, 100, 10, 9],
type: 'bar'
}, {
yAxisID: scaleID,
data: [10000, 10000, 10000, 10000, 10000, 10000],
hidden: true
hidden: true,
type: 'bar'
}]
};
@@ -230,7 +286,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -252,7 +310,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -285,7 +345,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -318,7 +380,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: {},
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -350,7 +414,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -379,7 +445,9 @@ describe('Logarithmic Scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -406,7 +474,9 @@ describe('Logarithmic Scale tests', function() {
var verticalScale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -431,7 +501,9 @@ describe('Logarithmic Scale tests', function() {
var horizontalScale = new Constructor({
ctx: mockContext,
options: horizontalConfig,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
+61 -13
Ver Arquivo
@@ -10,7 +10,7 @@ describe('Test the radial linear scale', function() {
var defaultConfig = Chart.scaleService.getScaleDefaults('radialLinear');
expect(defaultConfig).toEqual({
angleLines: {
show: true,
display: true,
color: "rgba(0, 0, 0, 0.1)",
lineWidth: 1
},
@@ -22,7 +22,7 @@ describe('Test the radial linear scale', function() {
drawTicks: true,
lineWidth: 1,
offsetGridLines: false,
show: true,
display: true,
zeroLineColor: "rgba(0,0,0,0.25)",
zeroLineWidth: 1,
},
@@ -40,7 +40,7 @@ describe('Test the radial linear scale', function() {
fontSize: 12,
fontStyle: 'normal',
labelString: '',
show: false,
display: false,
},
ticks: {
backdropColor: "rgba(255,255,255,0.75)",
@@ -57,7 +57,7 @@ describe('Test the radial linear scale', function() {
padding: 10,
reverse: false,
showLabelBackdrop: true,
show: true,
display: true,
callback: defaultConfig.ticks.callback, // make this nicer, then check explicitly below
},
@@ -86,7 +86,39 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('radialLinear'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
scale.update(200, 300);
expect(scale.min).toBe(-100);
expect(scale.max).toBe(200);
});
it('Should correctly determine the max & min of string data values', function() {
var scaleID = 'myScale';
var mockData = {
datasets: [{
yAxisID: scaleID,
data: ['10', '5', '0', '-5', '78', '-100']
}, {
yAxisID: scaleID,
data: ['150']
}],
labels: ['lablel1', 'label2', 'label3', 'label4', 'label5', 'label6']
};
var mockContext = window.createMockContext();
var Constructor = Chart.scaleService.getScaleConstructor('radialLinear');
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('radialLinear'), // use default config for scale
chart: {
data: mockData
},
id: scaleID,
});
@@ -118,7 +150,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('radialLinear'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -140,7 +174,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('radialLinear'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -166,7 +202,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -205,7 +243,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -238,7 +278,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -265,7 +307,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -297,7 +341,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
@@ -340,7 +386,9 @@ describe('Test the radial linear scale', function() {
var scale = new Constructor({
ctx: mockContext,
options: config,
data: mockData,
chart: {
data: mockData
},
id: scaleID,
});
+29 -8
Ver Arquivo
@@ -21,7 +21,7 @@ describe('Time scale tests', function() {
drawTicks: true,
lineWidth: 1,
offsetGridLines: false,
show: true,
display: true,
zeroLineColor: "rgba(0,0,0,0.25)",
zeroLineWidth: 1,
},
@@ -32,7 +32,7 @@ describe('Time scale tests', function() {
fontSize: 12,
fontStyle: 'normal',
labelString: '',
show: false,
display: false,
},
ticks: {
beginAtZero: false,
@@ -45,7 +45,7 @@ describe('Time scale tests', function() {
mirror: false,
padding: 10,
reverse: false,
show: true,
display: true,
callback: defaultConfig.ticks.callback, // make this nicer, then check explicitly below
},
time: {
@@ -53,6 +53,17 @@ describe('Time scale tests', function() {
unit: false,
round: false,
displayFormat: false,
displayFormats: {
'millisecond': 'SSS [ms]',
'second': 'h:mm:ss a', // 11:20:01 AM
'minute': 'h:mm:ss a', // 11:20:01 AM
'hour': 'MMM D, hA', // Sept 4, 5PM
'day': 'll', // Sep 4 2015
'week': 'll', // Week 46, or maybe "[W]WW - YYYY" ?
'month': 'MMM YYYY', // Sept 2015
'quarter': '[Q]Q - YYYY', // Q3
'year': 'YYYY', // 2015
},
}
});
@@ -72,7 +83,9 @@ describe('Time scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('time'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -97,7 +110,9 @@ describe('Time scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config, // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -121,7 +136,9 @@ describe('Time scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: config, // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -145,7 +162,9 @@ describe('Time scale tests', function() {
var scale = new Constructor({
ctx: mockContext,
options: Chart.scaleService.getScaleDefaults('time'), // use default config for scale
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
@@ -168,7 +187,9 @@ describe('Time scale tests', function() {
var verticalScale = new Constructor({
ctx: mockContext,
options: verticalScaleConfig,
data: mockData,
chart: {
data: mockData
},
id: scaleID
});
verticalScale.update(50, 400);