Browse Source

Fixing merge conflict.

pull/837/head
Ændrew Rininsland 10 years ago
parent
commit
f0fa4c1815
  1. 10
      .editorconfig
  2. 10
      .jshintrc
  3. 3
      Gruntfile.coffee
  4. 5
      README.md
  5. 12
      bower.json
  6. 209
      c3.css
  7. 537
      c3.js
  8. 2
      c3.min.css
  9. 10
      c3.min.js
  10. 4
      component.json
  11. 8
      package.json
  12. 4
      spec/api.data-spec.js
  13. 4
      spec/api.focus-spec.js
  14. 4
      spec/api.grid-spec.js
  15. 4
      spec/api.load-spec.js
  16. 4
      spec/api.zoom-spec.js
  17. 4
      spec/arc-spec.js
  18. 13
      spec/axis-spec.js
  19. 3
      spec/c3-spec.js
  20. 4
      spec/class-spec.js
  21. 4
      spec/core-spec.js
  22. 120
      spec/data-spec.js
  23. 6
      spec/domain-spec.js
  24. 44
      spec/grid-spec.js
  25. 20
      spec/interaction-spec.js
  26. 6
      spec/legend-spec.js
  27. 4
      spec/shape.bar-spec.js
  28. 4
      spec/shape.line-spec.js
  29. 60
      spec/tooltip-spec.js
  30. 4
      spec/type-spec.js
  31. 4
      spec/zoom-spec.js
  32. 13
      src/api.chart.js
  33. 4
      src/api.show.js
  34. 1
      src/api.transform.js
  35. 2
      src/arc.js
  36. 34
      src/axis.js
  37. 3
      src/c3.axis.js
  38. 2
      src/color.js
  39. 7
      src/config.js
  40. 119
      src/core.js
  41. 4
      src/data.js
  42. 24
      src/domain.js
  43. 3
      src/drag.js
  44. 12
      src/format.js
  45. 22
      src/grid.js
  46. 8
      src/interaction.js
  47. 7
      src/polyfill.js
  48. 11
      src/region.js
  49. 13
      src/shape.bar.js
  50. 52
      src/shape.line.js
  51. 135
      src/subchart.js
  52. 16
      src/text.js
  53. 44
      src/tooltip.js

10
.editorconfig

@ -0,0 +1,10 @@
# editorconfig.org
root = true
[*]
indent_style = space
indent_size = 4
end_of_line = lf
charset = utf-8
trim_trailing_whitespace = true
insert_final_newline = true

10
.jshintrc

@ -16,5 +16,13 @@
"loopfunc": true,
"bitwise": false,
"browser": true
"browser": true,
"globals": {
"describe": false,
"beforeEach": false,
"it": false,
"expect": false
}
}

3
Gruntfile.coffee

@ -1,5 +1,5 @@
module.exports = (grunt) ->
require('load-grunt-tasks') grunt, pattern: 'grunt-contrib-*'
require('load-grunt-tasks') grunt, pattern: ['grunt-contrib-*', 'grunt-sass']
grunt.initConfig
watch:
@ -72,6 +72,7 @@ module.exports = (grunt) ->
'src/api.chart.js',
'src/api.tooltip.js',
'src/c3.axis.js',
'src/polyfill.js',
'src/tail.js'
]
dest: 'c3.js'

5
README.md

@ -1,4 +1,4 @@
c3 [![Build Status](https://travis-ci.org/masayuki0812/c3.svg?branch=master)](https://travis-ci.org/masayuki0812/c3)
c3 [![Build Status](https://travis-ci.org/masayuki0812/c3.svg?branch=master)](https://travis-ci.org/masayuki0812/c3) [![Dependency Status](https://david-dm.org/masayuki0812/c3.svg)](https://david-dm.org/masayuki0812/c3) [![devDependency Status](https://david-dm.org/masayuki0812/c3/dev-status.svg)](https://david-dm.org/masayuki0812/c3#info=devDependencies) [![license](http://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat)](https://github.com/masayuki0812/c3/blob/master/LICENSE)
==
c3 is a D3-based reusable chart library that enables deeper integration of charts into web applications.
@ -42,6 +42,9 @@ If you choose to submit a pull request, please do not bump the version number un
Please fork this fiddle:
+ [http://jsfiddle.net/masayuki0812/7kYJu/](http://jsfiddle.net/masayuki0812/7kYJu/)
## Dependency
+ [D3.js](https://github.com/mbostock/d3) `<=3.5.0`
## License
MIT

12
bower.json

@ -4,7 +4,7 @@
"c3.css",
"c3.js"
],
"version": "0.4.8",
"version": "0.4.9",
"homepage": "https://github.com/masayuki0812/c3",
"authors": [
"Masayuki Tanaka <masayuki0812@mac.com>"
@ -19,10 +19,14 @@
"**/.*",
"node_modules",
"bower_components",
"test",
"tests"
"htdocs",
"spec",
"src",
"package.json",
"component.json",
"Gruntfile.*"
],
"dependencies": {
"d3": "~3.4.4"
"d3": "<=3.5.0"
}
}

209
c3.css

@ -1,217 +1,158 @@
/*-- Chart --*/
.c3 svg {
font: 10px sans-serif;
}
font: 10px sans-serif; }
.c3 path, .c3 line {
fill: none;
stroke: #000;
}
stroke: #000; }
.c3 text {
-webkit-user-select: none;
-moz-user-select: none;
user-select: none;
}
user-select: none; }
.c3-legend-item-tile,
.c3-xgrid-focus,
.c3-ygrid,
.c3-event-rect,
.c3-bars path {
shape-rendering: crispEdges;
}
.c3-legend-item-tile, .c3-xgrid-focus, .c3-ygrid, .c3-event-rect, .c3-bars path {
shape-rendering: crispEdges; }
.c3-chart-arc path {
stroke: #fff;
stroke: #fff; }
}
.c3-chart-arc text {
fill: #fff;
font-size: 13px;
}
font-size: 13px; }
/*-- Axis --*/
.c3-axis-x .tick {
}
.c3-axis-x-label {
}
.c3-axis-y .tick {
}
.c3-axis-y-label {
}
.c3-axis-y2 .tick {
}
.c3-axis-y2-label {
}
/*-- Grid --*/
.c3-grid line {
stroke: #aaa;
}
stroke: #aaa; }
.c3-grid text {
fill: #aaa;
}
fill: #aaa; }
.c3-xgrid, .c3-ygrid {
stroke-dasharray: 3 3;
}
.c3-xgrid-focus {
}
stroke-dasharray: 3 3; }
/*-- Text on Chart --*/
.c3-text {
}
.c3-text.c3-empty {
fill: #808080;
font-size: 2em;
}
font-size: 2em; }
/*-- Line --*/
.c3-line {
stroke-width: 1px;
}
/*-- Point --*/
stroke-width: 1px; }
/*-- Point --*/
.c3-circle._expanded_ {
stroke-width: 1px;
stroke: white;
}
stroke: white; }
.c3-selected-circle {
fill: white;
stroke-width: 2px;
}
stroke-width: 2px; }
/*-- Bar --*/
.c3-bar {
stroke-width: 0;
}
.c3-bar._expanded_ {
fill-opacity: 0.75;
}
/*-- Arc --*/
stroke-width: 0; }
.c3-chart-arcs-title {
dominant-baseline: middle;
font-size: 1.3em;
}
.c3-bar._expanded_ {
fill-opacity: 0.75; }
/*-- Focus --*/
.c3-target.c3-focused {
opacity: 1;
}
opacity: 1; }
.c3-target.c3-focused path.c3-line, .c3-target.c3-focused path.c3-step {
stroke-width: 2px;
}
.c3-target.c3-defocused {
opacity: 0.3 !important;
}
stroke-width: 2px; }
.c3-target.c3-defocused {
opacity: 0.3 !important; }
/*-- Region --*/
.c3-region {
fill: steelblue;
fill-opacity: .1;
}
fill-opacity: 0.1; }
/*-- Brush --*/
.c3-brush .extent {
fill-opacity: .1;
}
fill-opacity: 0.1; }
/*-- Select - Drag --*/
.c3-dragarea {
}
/*-- Legend --*/
.c3-legend-item {
font-size: 12px;
}
font-size: 12px; }
.c3-legend-item-hidden {
opacity: 0.15;
}
opacity: 0.15; }
.c3-legend-background {
opacity: 0.75;
fill: white;
stroke: lightgray;
stroke-width: 1
}
stroke-width: 1; }
/*-- Tooltip --*/
.c3-tooltip-container {
z-index: 10;
}
z-index: 10; }
.c3-tooltip {
border-collapse:collapse;
border-spacing:0;
background-color:#fff;
empty-cells:show;
-webkit-box-shadow: 7px 7px 12px -9px rgb(119,119,119);
-moz-box-shadow: 7px 7px 12px -9px rgb(119,119,119);
box-shadow: 7px 7px 12px -9px rgb(119,119,119);
opacity: 0.9;
}
border-collapse: collapse;
border-spacing: 0;
background-color: #fff;
empty-cells: show;
-webkit-box-shadow: 7px 7px 12px -9px #777777;
-moz-box-shadow: 7px 7px 12px -9px #777777;
box-shadow: 7px 7px 12px -9px #777777;
opacity: 0.9; }
.c3-tooltip tr {
border:1px solid #CCC;
}
border: 1px solid #CCC; }
.c3-tooltip th {
background-color: #aaa;
font-size:14px;
padding:2px 5px;
text-align:left;
color:#FFF;
}
font-size: 14px;
padding: 2px 5px;
text-align: left;
color: #FFF; }
.c3-tooltip td {
font-size:13px;
font-size: 13px;
padding: 3px 6px;
background-color:#fff;
border-left:1px dotted #999;
}
background-color: #fff;
border-left: 1px dotted #999; }
.c3-tooltip td > span {
display: inline-block;
width: 10px;
height: 10px;
margin-right: 6px;
}
.c3-tooltip td.value{
text-align: right;
}
margin-right: 6px; }
.c3-tooltip td.value {
text-align: right; }
/*-- Area --*/
.c3-area {
stroke-width: 0;
opacity: 0.2;
}
opacity: 0.2; }
/*-- Arc --*/
.c3-chart-arcs-title {
dominant-baseline: middle;
font-size: 1.3em; }
.c3-chart-arcs .c3-chart-arcs-background {
fill: #e0e0e0;
stroke: none;
}
stroke: none; }
.c3-chart-arcs .c3-chart-arcs-gauge-unit {
fill: #000;
font-size: 16px;
}
font-size: 16px; }
.c3-chart-arcs .c3-chart-arcs-gauge-max {
fill: #777;
}
fill: #777; }
.c3-chart-arcs .c3-chart-arcs-gauge-min {
fill: #777;
}
fill: #777; }
.c3-chart-arc .c3-gauge-value {
fill: #000;
/* font-size: 28px !important;*/
}
/* font-size: 28px !important;*/ }

537
c3.js

@ -3,7 +3,7 @@
/*global define, module, exports, require */
var c3 = { version: "0.4.8" };
var c3 = { version: "0.4.9" };
var c3_chart_fn, c3_chart_internal_fn;
@ -399,7 +399,7 @@
};
c3_chart_internal_fn.updateTargets = function (targets) {
var $$ = this, config = $$.config;
var $$ = this;
/*-- Main --*/
@ -413,14 +413,19 @@
$$.updateTargetsForLine(targets);
//-- Arc --//
if ($$.updateTargetsForArc) { $$.updateTargetsForArc(targets); }
if ($$.updateTargetsForSubchart) { $$.updateTargetsForSubchart(targets); }
if ($$.hasArcType() && $$.updateTargetsForArc) { $$.updateTargetsForArc(targets); }
/*-- Show --*/
/*-- Sub --*/
if ($$.updateTargetsForSubchart) { $$.updateTargetsForSubchart(targets); }
// Fade-in each chart
$$.showTargets();
};
c3_chart_internal_fn.showTargets = function () {
var $$ = this;
$$.svg.selectAll('.' + CLASS.target).filter(function (d) { return $$.isTargetToShow(d.id); })
.transition().duration(config.transition_duration)
.transition().duration($$.config.transition_duration)
.style("opacity", 1);
};
@ -475,13 +480,7 @@
if (targetsToShow.length) {
$$.updateXDomain(targetsToShow, withUpdateXDomain, withUpdateOrgXDomain, withTrimXDomain);
if (!config.axis_x_tick_values) {
if (config.axis_x_tick_fit || config.axis_x_tick_count) {
tickValues = $$.generateTickValues($$.mapTargetsToUniqueXs(targetsToShow), config.axis_x_tick_count, $$.isTimeSeries());
} else {
tickValues = undefined;
}
$$.xAxis.tickValues(tickValues);
$$.subXAxis.tickValues(tickValues);
tickValues = $$.updateXAxisTickValues(targetsToShow);
}
} else {
$$.xAxis.tickValues([]);
@ -556,22 +555,22 @@
.style('opacity', targetsToShow.length ? 0 : 1);
// grid
$$.redrawGrid(duration);
$$.updateGrid(duration);
// rect for regions
$$.redrawRegion(duration);
$$.updateRegion(duration);
// bars
$$.redrawBar(durationForExit);
$$.updateBar(durationForExit);
// lines, areas and cricles
$$.redrawLine(durationForExit);
$$.redrawArea(durationForExit);
$$.redrawCircle();
$$.updateLine(durationForExit);
$$.updateArea(durationForExit);
$$.updateCircle();
// text
if ($$.hasDataLabel()) {
$$.redrawText(durationForExit);
$$.updateText(durationForExit);
}
// arc
@ -601,24 +600,7 @@
cx = ($$.config.axis_rotated ? $$.circleY : $$.circleX).bind($$);
cy = ($$.config.axis_rotated ? $$.circleX : $$.circleY).bind($$);
// transition should be derived from one transition
d3.transition().duration(duration).each(function () {
var transitions = [];
$$.addTransitionForBar(transitions, drawBar);
$$.addTransitionForLine(transitions, drawLine);
$$.addTransitionForArea(transitions, drawArea);
$$.addTransitionForCircle(transitions, cx, cy);
$$.addTransitionForText(transitions, xForText, yForText, options.flow);
$$.addTransitionForRegion(transitions);
$$.addTransitionForGrid(transitions);
// Wait for end of transitions if called from flow API
if (options.flow) {
waitForDraw = $$.generateWait();
transitions.forEach(function (t) {
waitForDraw.add(t);
});
flow = $$.generateFlow({
targets: targetsToShow,
flow: options.flow,
@ -633,8 +615,54 @@
yForText: yForText
});
}
if (duration && $$.isTabVisible()) { // Only use transition if tab visible. See #938.
// transition should be derived from one transition
d3.transition().duration(duration).each(function () {
var transitionsToWait = [];
// redraw and gather transitions
[
$$.redrawBar(drawBar, true),
$$.redrawLine(drawLine, true),
$$.redrawArea(drawArea, true),
$$.redrawCircle(cx, cy, true),
$$.redrawText(xForText, yForText, options.flow, true),
$$.redrawRegion(true),
$$.redrawGrid(true),
].forEach(function (transitions) {
transitions.forEach(function (transition) {
transitionsToWait.push(transition);
});
});
// Wait for end of transitions to call flow and onrendered callback
waitForDraw = $$.generateWait();
transitionsToWait.forEach(function (t) {
waitForDraw.add(t);
});
})
.call(waitForDraw || function () {}, flow || function () {});
.call(waitForDraw, function () {
if (flow) {
flow();
}
if (config.onrendered) {
config.onrendered.call($$);
}
});
}
else {
$$.redrawBar(drawBar);
$$.redrawLine(drawLine);
$$.redrawArea(drawArea);
$$.redrawCircle(cx, cy);
$$.redrawText(xForText, yForText, options.flow);
$$.redrawRegion();
$$.redrawGrid();
if (config.onrendered) {
config.onrendered.call($$);
}
}
// update fadein condition
$$.mapToIds($$.data.targets).forEach(function (id) {
@ -929,6 +957,21 @@
return parsedDate;
};
c3_chart_internal_fn.isTabVisible = function () {
var hidden;
if (typeof document.hidden !== "undefined") { // Opera 12.10 and Firefox 18 and later support
hidden = "hidden";
} else if (typeof document.mozHidden !== "undefined") {
hidden = "mozHidden";
} else if (typeof document.msHidden !== "undefined") {
hidden = "msHidden";
} else if (typeof document.webkitHidden !== "undefined") {
hidden = "webkitHidden";
}
return document[hidden] ? false : true;
};
c3_chart_internal_fn.getDefaultConfig = function () {
var config = {
bindto: '#chart',
@ -951,6 +994,7 @@
onresize: function () {},
onresized: function () {},
oninit: function () {},
onrendered: function () {},
transition_duration: 350,
data_x: undefined,
data_xs: {},
@ -975,13 +1019,12 @@
data_selection_grouped: false,
data_selection_isselectable: function () { return true; },
data_selection_multiple: true,
data_selection_draggable: false,
data_onclick: function () {},
data_onmouseover: function () {},
data_onmouseout: function () {},
data_onselected: function () {},
data_onunselected: function () {},
data_ondragstart: function () {},
data_ondragend: function () {},
data_url: undefined,
data_json: undefined,
data_rows: undefined,
@ -1036,6 +1079,7 @@
axis_y_type: undefined,
axis_y_max: undefined,
axis_y_min: undefined,
axis_y_inverted: false,
axis_y_center: undefined,
axis_y_inner: undefined,
axis_y_label: {},
@ -1050,6 +1094,7 @@
axis_y2_show: false,
axis_y2_max: undefined,
axis_y2_min: undefined,
axis_y2_inverted: false,
axis_y2_center: undefined,
axis_y2_inner: undefined,
axis_y2_label: {},
@ -1114,6 +1159,7 @@
tooltip_format_title: undefined,
tooltip_format_name: undefined,
tooltip_format_value: undefined,
tooltip_position: undefined,
tooltip_contents: function (d, defaultTitleFormat, defaultValueFormat, color) {
return this.getTooltipContent ? this.getTooltipContent(d, defaultTitleFormat, defaultValueFormat, color) : '';
},
@ -1315,22 +1361,19 @@
yTargets = xDomain ? $$.filterByXDomain(targetsByAxisId, xDomain) : targetsByAxisId,
yMin = axisId === 'y2' ? config.axis_y2_min : config.axis_y_min,
yMax = axisId === 'y2' ? config.axis_y2_max : config.axis_y_max,
yDomainMin = isValue(yMin) ? yMin : $$.getYDomainMin(yTargets),
yDomainMax = isValue(yMax) ? yMax : $$.getYDomainMax(yTargets),
domainLength, padding, padding_top, padding_bottom,
yDomainMin = $$.getYDomainMin(yTargets),
yDomainMax = $$.getYDomainMax(yTargets),
domain, domainLength, padding, padding_top, padding_bottom,
center = axisId === 'y2' ? config.axis_y2_center : config.axis_y_center,
yDomainAbs, lengths, diff, ratio, isAllPositive, isAllNegative,
isZeroBased = ($$.hasType('bar', yTargets) && config.bar_zerobased) || ($$.hasType('area', yTargets) && config.area_zerobased),
isInverted = axisId === 'y2' ? config.axis_y2_inverted : config.axis_y_inverted,
showHorizontalDataLabel = $$.hasDataLabel() && config.axis_rotated,
showVerticalDataLabel = $$.hasDataLabel() && !config.axis_rotated;
if (yDomainMax < yDomainMin) {
if (isValue(yMin)) {
yDomainMax = yDomainMin + 10; // TODO: introduce axis.y.maxMin
} else {
yDomainMin = yDomainMax - 10; // TODO: introduce axis.y.minMax
}
}
// MEMO: avoid inverting domain unexpectedly
yDomainMin = isValue(yMin) ? yMin : isValue(yMax) ? (yDomainMin < yMax ? yDomainMin : yMax - 10) : yDomainMin;
yDomainMax = isValue(yMax) ? yMax : isValue(yMin) ? (yMin < yDomainMax ? yDomainMax : yMin + 10) : yDomainMax;
if (yTargets.length === 0) { // use current domain if target of axisId is none
return axisId === 'y2' ? $$.y2.domain() : $$.y.domain();
@ -1368,13 +1411,13 @@
}
// add padding for data label
if (showHorizontalDataLabel) {
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, axisId, 'width');
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, 'width');
diff = diffDomain($$.y.range());
ratio = [lengths[0] / diff, lengths[1] / diff];
padding_top += domainLength * (ratio[1] / (1 - ratio[0] - ratio[1]));
padding_bottom += domainLength * (ratio[0] / (1 - ratio[0] - ratio[1]));
} else if (showVerticalDataLabel) {
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, axisId, 'height');
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, 'height');
padding_top += this.convertPixelsToAxisPadding(lengths[1], domainLength);
padding_bottom += this.convertPixelsToAxisPadding(lengths[0], domainLength);
}
@ -1391,7 +1434,8 @@
if (isAllPositive) { padding_bottom = yDomainMin; }
if (isAllNegative) { padding_top = -yDomainMax; }
}
return [yDomainMin - padding_bottom, yDomainMax + padding_top];
domain = [yDomainMin - padding_bottom, yDomainMax + padding_top];
return isInverted ? domain.reverse() : domain;
};
c3_chart_internal_fn.getXDomainMin = function (targets) {
var $$ = this, config = $$.config;
@ -1747,13 +1791,13 @@
}
return false;
};
c3_chart_internal_fn.getDataLabelLength = function (min, max, axisId, key) {
c3_chart_internal_fn.getDataLabelLength = function (min, max, key) {
var $$ = this,
lengths = [0, 0], paddingCoef = 1.3;
$$.selectChart.select('svg').selectAll('.dummy')
.data([min, max])
.enter().append('text')
.text(function (d) { return $$.formatByAxisId(axisId)(d); })
.text(function (d) { return $$.dataLabelFormat(d.id)(d); })
.each(function (d, i) {
lengths[i] = this.getBoundingClientRect()[key] * paddingCoef;
})
@ -2312,7 +2356,7 @@
});
if (config.tooltip_grouped) {
$$.showTooltip(selectedData, d3.mouse(this));
$$.showTooltip(selectedData, this);
$$.showXGridFocus(selectedData);
}
@ -2343,7 +2387,7 @@
eventRect.style('cursor', 'pointer');
}
if (!config.tooltip_grouped) {
$$.showTooltip([d], d3.mouse(this));
$$.showTooltip([d], this);
$$.showXGridFocus([d]);
if (config.point_focus_expand_enabled) { $$.expandCircles(index, d.id, true); }
$$.expandBars(index, d.id, true);
@ -2368,10 +2412,12 @@
});
})
.call(
config.data_selection_draggable && $$.drag ? (
d3.behavior.drag().origin(Object)
.on('drag', function () { $$.drag(d3.mouse(this)); })
.on('dragstart', function () { $$.dragstart(d3.mouse(this)); })
.on('dragend', function () { $$.dragend(); })
) : function () {}
);
};
@ -2426,7 +2472,7 @@
selectedData = sameXData.map(function (d) {
return $$.addName(d);
});
$$.showTooltip(selectedData, mouse);
$$.showTooltip(selectedData, this);
// expand points
if (config.point_focus_expand_enabled) {
@ -2712,7 +2758,7 @@
// MEMO: can not keep same color...
//mainLineUpdate.exit().remove();
};
c3_chart_internal_fn.redrawLine = function (durationForExit) {
c3_chart_internal_fn.updateLine = function (durationForExit) {
var $$ = this;
$$.mainLine = $$.main.selectAll('.' + CLASS.lines).selectAll('.' + CLASS.line)
.data($$.lineData.bind($$));
@ -2727,12 +2773,13 @@
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForLine = function (transitions, drawLine) {
var $$ = this;
transitions.push($$.mainLine.transition()
c3_chart_internal_fn.redrawLine = function (drawLine, withTransition) {
return [
(withTransition ? this.mainLine.transition() : this.mainLine)
.attr("d", drawLine)
.style("stroke", $$.color)
.style("opacity", 1));
.style("stroke", this.color)
.style("opacity", 1)
];
};
c3_chart_internal_fn.generateDrawLine = function (lineIndices, isSub) {
var $$ = this, config = $$.config,
@ -2872,7 +2919,7 @@
};
c3_chart_internal_fn.redrawArea = function (durationForExit) {
c3_chart_internal_fn.updateArea = function (durationForExit) {
var $$ = this, d3 = $$.d3;
$$.mainArea = $$.main.selectAll('.' + CLASS.areas).selectAll('.' + CLASS.area)
.data($$.lineData.bind($$));
@ -2886,12 +2933,13 @@
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForArea = function (transitions, drawArea) {
var $$ = this;
transitions.push($$.mainArea.transition()
c3_chart_internal_fn.redrawArea = function (drawArea, withTransition) {
return [
(withTransition ? this.mainArea.transition() : this.mainArea)
.attr("d", drawArea)
.style("fill", $$.color)
.style("opacity", $$.orgAreaOpacity));
.style("fill", this.color)
.style("opacity", this.orgAreaOpacity)
];
};
c3_chart_internal_fn.generateDrawArea = function (areaIndices, isSub) {
var $$ = this, config = $$.config, area = $$.d3.svg.area(),
@ -2899,7 +2947,7 @@
yScaleGetter = isSub ? $$.getSubYScale : $$.getYScale,
xValue = function (d) { return (isSub ? $$.subxx : $$.xx).call($$, d); },
value0 = function (d, i) {
return config.data_groups.length > 0 ? getPoints(d, i)[0][1] : yScaleGetter.call($$, d.id)(0);
return config.data_groups.length > 0 ? getPoints(d, i)[0][1] : yScaleGetter.call($$, d.id)($$.getAreaBaseValue(d.id));
},
value1 = function (d, i) {
return config.data_groups.length > 0 ? getPoints(d, i)[1][1] : yScaleGetter.call($$, d.id)(d.value);
@ -2926,7 +2974,9 @@
return path ? path : "M 0 0";
};
};
c3_chart_internal_fn.getAreaBaseValue = function () {
return 0;
};
c3_chart_internal_fn.generateGetAreaPoints = function (areaIndices, isSub) { // partial duplication of generateGetBarPoints
var $$ = this, config = $$.config,
areaTargetsNum = areaIndices.__max__ + 1,
@ -2953,7 +3003,7 @@
};
c3_chart_internal_fn.redrawCircle = function () {
c3_chart_internal_fn.updateCircle = function () {
var $$ = this;
$$.mainCircle = $$.main.selectAll('.' + CLASS.circles).selectAll('.' + CLASS.circle)
.data($$.lineOrScatterData.bind($$));
@ -2965,16 +3015,18 @@
.style("opacity", $$.initialOpacityForCircle.bind($$));
$$.mainCircle.exit().remove();
};
c3_chart_internal_fn.addTransitionForCircle = function (transitions, cx, cy) {
var $$ = this;
transitions.push($$.mainCircle.transition()
.style('opacity', $$.opacityForCircle.bind($$))
.style("fill", $$.color)
c3_chart_internal_fn.redrawCircle = function (cx, cy, withTransition) {
var selectedCircles = this.main.selectAll('.' + CLASS.selectedCircle);
return [
(withTransition ? this.mainCircle.transition() : this.mainCircle)
.style('opacity', this.opacityForCircle.bind(this))
.style("fill", this.color)
.attr("cx", cx)
.attr("cy", cy));
transitions.push($$.main.selectAll('.' + CLASS.selectedCircle).transition()
.attr("cy", cy),
(withTransition ? selectedCircles.transition() : selectedCircles)
.attr("cx", cx)
.attr("cy", cy));
.attr("cy", cy)
];
};
c3_chart_internal_fn.circleX = function (d) {
return d.x || d.x === 0 ? this.x(d.x) : null;
@ -3059,7 +3111,7 @@
.style("cursor", function (d) { return config.data_selection_isselectable(d) ? "pointer" : null; });
};
c3_chart_internal_fn.redrawBar = function (durationForExit) {
c3_chart_internal_fn.updateBar = function (durationForExit) {
var $$ = this,
barData = $$.barData.bind($$),
classBar = $$.classBar.bind($$),
@ -3077,12 +3129,13 @@
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForBar = function (transitions, drawBar) {
var $$ = this;
transitions.push($$.mainBar.transition()
c3_chart_internal_fn.redrawBar = function (drawBar, withTransition) {
return [
(withTransition ? this.mainBar.transition() : this.mainBar)
.attr('d', drawBar)
.style("fill", $$.color)
.style("opacity", 1));
.style("fill", this.color)
.style("opacity", 1)
];
};
c3_chart_internal_fn.getBarW = function (axis, barTargetsNum) {
var $$ = this, config = $$.config,
@ -3178,7 +3231,7 @@
mainTextEnter.append('g')
.attr('class', classTexts);
};
c3_chart_internal_fn.redrawText = function (durationForExit) {
c3_chart_internal_fn.updateText = function (durationForExit) {
var $$ = this, config = $$.config,
barOrLineData = $$.barOrLineData.bind($$),
classText = $$.classText.bind($$);
@ -3191,20 +3244,20 @@
.style("fill", function (d) { return $$.color(d); })
.style("fill-opacity", 0);
$$.mainText
.text(function (d, i, j) { return $$.formatByAxisId($$.getAxisId(d.id))(d.value, d.id, i, j); });
.text(function (d, i, j) { return $$.dataLabelFormat(d.id)(d.value, d.id, i, j); });
$$.mainText.exit()
.transition().duration(durationForExit)
.style('fill-opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForText = function (transitions, xForText, yForText, forFlow) {
var $$ = this,
opacityForText = forFlow ? 0 : $$.opacityForText.bind($$);
transitions.push($$.mainText.transition()
c3_chart_internal_fn.redrawText = function (xForText, yForText, forFlow, withTransition) {
return [
(withTransition ? this.mainText.transition() : this.mainText)
.attr('x', xForText)
.attr('y', yForText)
.style("fill", $$.color)
.style("fill-opacity", opacityForText));
.style("fill", this.color)
.style("fill-opacity", forFlow ? 0 : this.opacityForText.bind(this))
];
};
c3_chart_internal_fn.getTextRect = function (text, cls) {
var body = this.d3.select('body').classed('c3', true),
@ -3432,7 +3485,7 @@
};
c3_chart_internal_fn.redrawGrid = function (duration) {
c3_chart_internal_fn.updateGrid = function (duration) {
var $$ = this, main = $$.main, config = $$.config,
xgridLine, ygridLine, yv;
@ -3453,7 +3506,7 @@
xgridLine.append('text')
.attr("text-anchor", "end")
.attr("transform", config.axis_rotated ? "" : "rotate(-90)")
.attr('dx', config.axis_rotated ? 0 : -$$.margin.top)
.attr('dx', -4)
.attr('dy', -5)
.style("opacity", 0);
// udpate
@ -3500,19 +3553,23 @@
.style("opacity", 0)
.remove();
};
c3_chart_internal_fn.addTransitionForGrid = function (transitions) {
var $$ = this, config = $$.config, xv = $$.xv.bind($$);
transitions.push($$.xgridLines.select('line').transition()
c3_chart_internal_fn.redrawGrid = function (withTransition) {
var $$ = this, config = $$.config, xv = $$.xv.bind($$),
lines = $$.xgridLines.select('line'),
texts = $$.xgridLines.select('text');
return [
(withTransition ? lines.transition() : lines)
.attr("x1", config.axis_rotated ? 0 : xv)
.attr("x2", config.axis_rotated ? $$.width : xv)
.attr("y1", config.axis_rotated ? xv : $$.margin.top)
.attr("y1", config.axis_rotated ? xv : 0)
.attr("y2", config.axis_rotated ? xv : $$.height)
.style("opacity", 1));
transitions.push($$.xgridLines.select('text').transition()
.style("opacity", 1),
(withTransition ? texts.transition() : texts)
.attr("x", config.axis_rotated ? $$.width : 0)
.attr("y", xv)
.text(function (d) { return d.text; })
.style("opacity", 1));
.style("opacity", 1)
];
};
c3_chart_internal_fn.showXGridFocus = function (selectedData) {
var $$ = this, config = $$.config,
@ -3626,8 +3683,9 @@
text = "<table class='" + CLASS.tooltip + "'>" + (title || title === 0 ? "<tr><th colspan='2'>" + title + "</th></tr>" : "");
}
name = nameFormat(d[i].name, d[i].ratio, d[i].id, d[i].index);
value = valueFormat(d[i].value, d[i].ratio, d[i].id, d[i].index);
if (value !== undefined) {
name = nameFormat(d[i].name, d[i].ratio, d[i].id, d[i].index);
bgcolor = $$.levelColor ? $$.levelColor(d[i].value) : color(d[i].id);
text += "<tr class='" + CLASS.tooltipName + "-" + d[i].id + "'>";
@ -3635,24 +3693,17 @@
text += "<td class='value'>" + value + "</td>";
text += "</tr>";
}
}
return text + "</table>";
};
c3_chart_internal_fn.showTooltip = function (selectedData, mouse) {
var $$ = this, config = $$.config;
var tWidth, tHeight, svgLeft, tooltipLeft, tooltipRight, tooltipTop, chartRight;
c3_chart_internal_fn.tooltipPosition = function (dataToShow, tWidth, tHeight, element) {
var $$ = this, config = $$.config, d3 = $$.d3;
var svgLeft, tooltipLeft, tooltipRight, tooltipTop, chartRight;
var forArc = $$.hasArcType(),
dataToShow = selectedData.filter(function (d) { return d && isValue(d.value); });
if (dataToShow.length === 0 || !config.tooltip_show) {
return;
}
$$.tooltip.html(config.tooltip_contents.call($$, selectedData, $$.getXAxisTickFormat(), $$.getYFormat(forArc), $$.color)).style("display", "block");
// Get tooltip dimensions
tWidth = $$.tooltip.property('offsetWidth');
tHeight = $$.tooltip.property('offsetHeight');
mouse = d3.mouse(element);
// Determin tooltip position
if (forArc) {
tooltipLeft = ($$.width / 2) + mouse[0];
tooltipLeft = (($$.width - ($$.isLegendRight ? $$.getLegendWidth() : 0)) / 2) + mouse[0];
tooltipTop = ($$.height / 2) + mouse[1] + 20;
} else {
svgLeft = $$.getSvgLeft(true);
@ -3678,10 +3729,28 @@
if (tooltipTop < 0) {
tooltipTop = 0;
}
return {top: tooltipTop, left: tooltipLeft};
};
c3_chart_internal_fn.showTooltip = function (selectedData, element) {
var $$ = this, config = $$.config;
var tWidth, tHeight, position;
var forArc = $$.hasArcType(),
dataToShow = selectedData.filter(function (d) { return d && isValue(d.value); }),
positionFunction = config.tooltip_position || c3_chart_internal_fn.tooltipPosition;
if (dataToShow.length === 0 || !config.tooltip_show) {
return;
}
$$.tooltip.html(config.tooltip_contents.call($$, selectedData, $$.getXAxisTickFormat(), $$.getYFormat(forArc), $$.color)).style("display", "block");
// Get tooltip dimensions
tWidth = $$.tooltip.property('offsetWidth');
tHeight = $$.tooltip.property('offsetHeight');
position = positionFunction.call(this, dataToShow, tWidth, tHeight, element);
// Set tooltip
$$.tooltip
.style("top", tooltipTop + "px")
.style("left", tooltipLeft + 'px');
.style("top", position.top + "px")
.style("left", position.left + 'px');
};
c3_chart_internal_fn.hideTooltip = function () {
this.tooltip.style("display", "none");
@ -4052,13 +4121,14 @@
.attr("transform", config.axis_rotated ? "" : "rotate(-90)")
.style("text-anchor", $$.textAnchorForY2AxisLabel.bind($$));
};
c3_chart_internal_fn.getXAxis = function (scale, orient, tickFormat, tickValues, withOuterTick) {
c3_chart_internal_fn.getXAxis = function (scale, orient, tickFormat, tickValues, withOuterTick, withoutTransition) {
var $$ = this, config = $$.config,
axisParams = {
isCategory: $$.isCategorized(),
withOuterTick: withOuterTick,
tickMultiline: config.axis_x_tick_multiline,
tickWidth: config.axis_x_tick_width
tickWidth: config.axis_x_tick_width,
withoutTransition: withoutTransition,
},
axis = c3_axis($$.d3, axisParams).scale(scale).orient(orient);
@ -4085,6 +4155,19 @@
return axis;
};
c3_chart_internal_fn.updateXAxisTickValues = function (targets, axis) {
var $$ = this, config = $$.config, tickValues;
if (config.axis_x_tick_fit || config.axis_x_tick_count) {
tickValues = $$.generateTickValues($$.mapTargetsToUniqueXs(targets), config.axis_x_tick_count, $$.isTimeSeries());
}
if (axis) {
axis.tickValues(tickValues);
} else {
$$.xAxis.tickValues(tickValues);
$$.subXAxis.tickValues(tickValues);
}
return tickValues;
};
c3_chart_internal_fn.getYAxis = function (scale, orient, tickFormat, tickValues, withOuterTick) {
var axisParams = {withOuterTick: withOuterTick},
axis = c3_axis(this.d3, axisParams).scale(scale).orient(orient).tickFormat(tickFormat);
@ -4288,7 +4371,7 @@
c3_chart_internal_fn.getMaxTickWidth = function (id, withoutRecompute) {
var $$ = this, config = $$.config,
maxWidth = 0, targetsToShow, scale, axis;
maxWidth = 0, targetsToShow, scale, axis, body, svg;
if (withoutRecompute && $$.currentMaxTickWidths[id]) {
return $$.currentMaxTickWidths[id];
}
@ -4303,13 +4386,21 @@
} else {
scale = $$.x.copy().domain($$.getXDomain(targetsToShow));
axis = $$.getXAxis(scale, $$.xOrient, $$.xAxisTickFormat, $$.xAxisTickValues);
$$.updateXAxisTickValues(targetsToShow, axis);
}
$$.d3.select('body').append("g").style('visibility', 'hidden').call(axis).each(function () {
body = this.d3.select('body').classed('c3', true);
svg = body.append('svg').style('visibility', 'hidden');
svg.append('g').call(axis).each(function () {
$$.d3.select(this).selectAll('text tspan').each(function () {
var box = this.getBoundingClientRect();
if (box.left > 0 && maxWidth < box.width) { maxWidth = box.width; }
if (box.left >= 0 && maxWidth < box.width) { maxWidth = box.width; }
});
});
}).remove();
// TODO: time lag to get maxWidth
window.setTimeout(function () {
svg.remove();
}, 100);
body.classed('c3', false);
}
$$.currentMaxTickWidths[id] = maxWidth <= 0 ? $$.currentMaxTickWidths[id] : maxWidth;
return $$.currentMaxTickWidths[id];
@ -4738,7 +4829,7 @@
var updated = $$.updateAngle(d),
arcData = $$.convertToArcData(updated),
selectedData = [arcData];
$$.showTooltip(selectedData, d3.mouse(this));
$$.showTooltip(selectedData, this);
} : null)
.on('mouseout', config.interaction_enabled ? function (d) {
var updated, arcData;
@ -4858,7 +4949,7 @@
.attr("clip-path", $$.clipPath)
.attr("class", CLASS.regions);
};
c3_chart_internal_fn.redrawRegion = function (duration) {
c3_chart_internal_fn.updateRegion = function (duration) {
var $$ = this, config = $$.config;
// hide if arc type
@ -4874,18 +4965,21 @@
.style("opacity", 0)
.remove();
};
c3_chart_internal_fn.addTransitionForRegion = function (transitions) {
c3_chart_internal_fn.redrawRegion = function (withTransition) {
var $$ = this,
regions = $$.mainRegion.selectAll('rect'),
x = $$.regionX.bind($$),
y = $$.regionY.bind($$),
w = $$.regionWidth.bind($$),
h = $$.regionHeight.bind($$);
transitions.push($$.mainRegion.selectAll('rect').transition()
return [
(withTransition ? regions.transition() : regions)
.attr("x", x)
.attr("y", y)
.attr("width", w)
.attr("height", h)
.style("fill-opacity", function (d) { return isValue(d.opacity) ? d.opacity : 0.1; }));
.style("fill-opacity", function (d) { return isValue(d.opacity) ? d.opacity : 0.1; })
];
};
c3_chart_internal_fn.regionX = function (d) {
var $$ = this, config = $$.config,
@ -4998,7 +5092,6 @@
.attr('class', CLASS.dragarea)
.style('opacity', 0.1);
$$.dragging = true;
$$.config.data_ondragstart.call($$.api);
};
c3_chart_internal_fn.dragend = function () {
@ -5012,10 +5105,8 @@
$$.main.selectAll('.' + CLASS.shape)
.classed(CLASS.INCLUDED, false);
$$.dragging = false;
$$.config.data_ondragend.call($$.api);
};
c3_chart_internal_fn.selectPoint = function (target, d, i) {
var $$ = this, config = $$.config,
cx = (config.axis_rotated ? $$.circleY : $$.circleX).bind($$),
@ -5107,9 +5198,7 @@
var $$ = this, config = $$.config,
context = $$.context = $$.svg.append("g").attr("transform", $$.getTranslate('context'));
if (!config.subchart_show) {
context.style('visibility', 'hidden');
}
context.style('visibility', config.subchart_show ? 'visible' : 'hidden');
// Define g for chart area
context.append('g')
@ -5128,9 +5217,7 @@
context.append("g")
.attr("clip-path", $$.clipPath)
.attr("class", CLASS.brush)
.call($$.brush)
.selectAll("rect")
.attr(config.axis_rotated ? "width" : "height", config.axis_rotated ? $$.width2 : $$.height2);
.call($$.brush);
// ATTENTION: This must be called AFTER chart added
// Add Axis
@ -5149,6 +5236,7 @@
classAreas = $$.classAreas.bind($$);
if (config.subchart_show) {
//-- Bar --//
contextBarUpdate = context.select('.' + CLASS.chartBars).selectAll('.' + CLASS.chartBar)
.data(targets)
.attr('class', classChartBar);
@ -5172,17 +5260,74 @@
// Area
contextLineEnter.append("g")
.attr("class", classAreas);
//-- Brush --//
context.selectAll('.' + CLASS.brush + ' rect')
.attr(config.axis_rotated ? "width" : "height", config.axis_rotated ? $$.width2 : $$.height2);
}
};
c3_chart_internal_fn.updateBarForSubchart = function (durationForExit) {
var $$ = this;
$$.contextBar = $$.context.selectAll('.' + CLASS.bars).selectAll('.' + CLASS.bar)
.data($$.barData.bind($$));
$$.contextBar.enter().append('path')
.attr("class", $$.classBar.bind($$))
.style("stroke", 'none')
.style("fill", $$.color);
$$.contextBar
.style("opacity", $$.initialOpacity.bind($$));
$$.contextBar.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.redrawBarForSubchart = function (drawBarOnSub, withTransition, duration) {
(withTransition ? this.contextBar.transition().duration(duration) : this.contextBar)
.attr('d', drawBarOnSub)
.style('opacity', 1);
};
c3_chart_internal_fn.updateLineForSubchart = function (durationForExit) {
var $$ = this;
$$.contextLine = $$.context.selectAll('.' + CLASS.lines).selectAll('.' + CLASS.line)
.data($$.lineData.bind($$));
$$.contextLine.enter().append('path')
.attr('class', $$.classLine.bind($$))
.style('stroke', $$.color);
$$.contextLine
.style("opacity", $$.initialOpacity.bind($$));
$$.contextLine.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.redrawLineForSubchart = function (drawLineOnSub, withTransition, duration) {
(withTransition ? this.contextLine.transition().duration(duration) : this.contextLine)
.attr("d", drawLineOnSub)
.style('opacity', 1);
};
c3_chart_internal_fn.updateAreaForSubchart = function (durationForExit) {
var $$ = this, d3 = $$.d3;
$$.contextArea = $$.context.selectAll('.' + CLASS.areas).selectAll('.' + CLASS.area)
.data($$.lineData.bind($$));
$$.contextArea.enter().append('path')
.attr("class", $$.classArea.bind($$))
.style("fill", $$.color)
.style("opacity", function () { $$.orgAreaOpacity = +d3.select(this).style('opacity'); return 0; });
$$.contextArea
.style("opacity", 0);
$$.contextArea.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.redrawAreaForSubchart = function (drawAreaOnSub, withTransition, duration) {
(withTransition ? this.contextArea.transition().duration(duration) : this.contextArea)
.attr("d", drawAreaOnSub)
.style("fill", this.color)
.style("opacity", this.orgAreaOpacity);
};
c3_chart_internal_fn.redrawSubchart = function (withSubchart, transitions, duration, durationForExit, areaIndices, barIndices, lineIndices) {
var $$ = this, d3 = $$.d3, context = $$.context, config = $$.config,
contextLine, contextArea, contextBar, drawAreaOnSub, drawBarOnSub, drawLineOnSub,
barData = $$.barData.bind($$),
lineData = $$.lineData.bind($$),
classBar = $$.classBar.bind($$),
classLine = $$.classLine.bind($$),
classArea = $$.classArea.bind($$),
initialOpacity = $$.initialOpacity.bind($$);
var $$ = this, d3 = $$.d3, config = $$.config,
drawAreaOnSub, drawBarOnSub, drawLineOnSub;
$$.context.style('visibility', config.subchart_show ? 'visible' : 'hidden');
// subchart
if (config.subchart_show) {
@ -5201,51 +5346,14 @@
drawAreaOnSub = $$.generateDrawArea(areaIndices, true);
drawBarOnSub = $$.generateDrawBar(barIndices, true);
drawLineOnSub = $$.generateDrawLine(lineIndices, true);
// bars
contextBar = context.selectAll('.' + CLASS.bars).selectAll('.' + CLASS.bar)
.data(barData);
contextBar.enter().append('path')
.attr("class", classBar)
.style("stroke", 'none')
.style("fill", $$.color);
contextBar
.style("opacity", initialOpacity)
.transition().duration(duration)
.attr('d', drawBarOnSub)
.style('opacity', 1);
contextBar.exit().transition().duration(duration)
.style('opacity', 0)
.remove();
// lines
contextLine = context.selectAll('.' + CLASS.lines).selectAll('.' + CLASS.line)
.data(lineData);
contextLine.enter().append('path')
.attr('class', classLine)
.style('stroke', $$.color);
contextLine
.style("opacity", initialOpacity)
.transition().duration(duration)
.attr("d", drawLineOnSub)
.style('opacity', 1);
contextLine.exit().transition().duration(duration)
.style('opacity', 0)
.remove();
// area
contextArea = context.selectAll('.' + CLASS.areas).selectAll('.' + CLASS.area)
.data(lineData);
contextArea.enter().append('path')
.attr("class", classArea)
.style("fill", $$.color)
.style("opacity", function () { $$.orgAreaOpacity = +d3.select(this).style('opacity'); return 0; });
contextArea
.style("opacity", 0)
.transition().duration(duration)
.attr("d", drawAreaOnSub)
.style("fill", $$.color)
.style("opacity", $$.orgAreaOpacity);
contextArea.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
$$.updateBarForSubchart(duration);
$$.updateLineForSubchart(duration);
$$.updateAreaForSubchart(duration);
$$.redrawBarForSubchart(drawBarOnSub, duration, duration);
$$.redrawLineForSubchart(drawLineOnSub, duration, duration);
$$.redrawAreaForSubchart(drawAreaOnSub, duration, duration);
}
}
};
@ -5358,7 +5466,7 @@
ids = [];
return function (d) {
var id = d.id || d, color;
var id = d.id || (d.data && d.data.id) || d, color;
// if callback function is provided
if (colors[id] instanceof Function) {
@ -5422,16 +5530,20 @@
c3_chart_internal_fn.defaultArcValueFormat = function (v, ratio) {
return (ratio * 100).toFixed(1) + '%';
};
c3_chart_internal_fn.formatByAxisId = function (axisId) {
c3_chart_internal_fn.dataLabelFormat = function (targetId) {
var $$ = this, data_labels = $$.config.data_labels,
format = function (v) { return isValue(v) ? +v : ""; };
format, defaultFormat = function (v) { return isValue(v) ? +v : ""; };
// find format according to axis id
if (typeof data_labels.format === 'function') {
format = data_labels.format;
} else if (typeof data_labels.format === 'object') {
if (data_labels.format[axisId]) {
format = data_labels.format[axisId];
if (data_labels.format[targetId]) {
format = data_labels.format[targetId] === true ? defaultFormat : data_labels.format[targetId];
} else {
format = function () { return ''; };
}
} else {
format = defaultFormat;
}
return format;
};
@ -5776,10 +5888,10 @@
$$.redraw({withUpdateOrgXDomain: true, withUpdateXDomain: true, withLegend: true});
};
c3_chart_fn.toggle = function (targetIds) {
c3_chart_fn.toggle = function (targetIds, options) {
var that = this, $$ = this.internal;
$$.mapToTargetIds(targetIds).forEach(function (targetId) {
$$.isTargetToShow(targetId) ? that.hide(targetId) : that.show(targetId);
$$.isTargetToShow(targetId) ? that.hide(targetId, options) : that.show(targetId, options);
});
};
@ -6221,6 +6333,7 @@
options.withTransitionForTransform = false;
$$.transiting = false;
$$.setTargetType(targetIds, type);
$$.updateTargets($$.data.targets); // this is needed when transforming to arc
$$.updateAndRedraw(options);
};
@ -6459,11 +6572,18 @@
c3_chart_fn.destroy = function () {
var $$ = this.internal;
$$.data.targets = undefined;
$$.data.xs = {};
$$.selectChart.classed('c3', false).html("");
window.clearInterval($$.intervalForObserveInserted);
window.onresize = null;
$$.selectChart.classed('c3', false).html("");
// MEMO: this is needed because the reference of some elements will not be released, then memory leak will happen.
Object.keys($$).forEach(function (key) {
$$[key] = null;
});
return null;
};
c3_chart_fn.tooltip = function () {};
@ -6552,7 +6672,8 @@
return newScale;
}
function textFormatted(v) {
return tickFormat ? tickFormat(v) : v;
var formatted = tickFormat ? tickFormat(v) : v;
return typeof formatted !== 'undefined' ? formatted : '';
}
function getSizeFor1Char(tick) {
if (tickTextCharSize) {
@ -6788,6 +6909,14 @@
return axis;
}
// fix problems using c3 with phantomjs #578
Function.prototype.bind = Function.prototype.bind || function (thisp) {
var fn = this;
return function () {
return fn.apply(thisp, arguments);
};
};
if (typeof define === 'function' && define.amd) {
define("c3", ["d3"], c3);
} else if ('undefined' !== typeof exports && 'undefined' !== typeof module) {

2
c3.min.css vendored

@ -1 +1 @@
.c3 svg{font:10px sans-serif}.c3 line,.c3 path{fill:none;stroke:#000}.c3 text{-webkit-user-select:none;-moz-user-select:none;user-select:none}.c3-bars path,.c3-event-rect,.c3-legend-item-tile,.c3-xgrid-focus,.c3-ygrid{shape-rendering:crispEdges}.c3-chart-arc path{stroke:#fff}.c3-chart-arc text{fill:#fff;font-size:13px}.c3-grid line{stroke:#aaa}.c3-grid text{fill:#aaa}.c3-xgrid,.c3-ygrid{stroke-dasharray:3 3}.c3-text.c3-empty{fill:gray;font-size:2em}.c3-line{stroke-width:1px}.c3-circle._expanded_{stroke-width:1px;stroke:#fff}.c3-selected-circle{fill:#fff;stroke-width:2px}.c3-bar{stroke-width:0}.c3-bar._expanded_{fill-opacity:.75}.c3-chart-arcs-title{dominant-baseline:middle;font-size:1.3em}.c3-target.c3-focused{opacity:1}.c3-target.c3-focused path.c3-line,.c3-target.c3-focused path.c3-step{stroke-width:2px}.c3-target.c3-defocused{opacity:.3!important}.c3-region{fill:#4682b4;fill-opacity:.1}.c3-brush .extent{fill-opacity:.1}.c3-legend-item{font-size:12px}.c3-legend-item-hidden{opacity:.15}.c3-legend-background{opacity:.75;fill:#fff;stroke:#d3d3d3;stroke-width:1}.c3-tooltip-container{z-index:10}.c3-tooltip{border-collapse:collapse;border-spacing:0;background-color:#fff;empty-cells:show;-webkit-box-shadow:7px 7px 12px -9px #777;-moz-box-shadow:7px 7px 12px -9px #777;box-shadow:7px 7px 12px -9px #777;opacity:.9}.c3-tooltip tr{border:1px solid #CCC}.c3-tooltip th{background-color:#aaa;font-size:14px;padding:2px 5px;text-align:left;color:#FFF}.c3-tooltip td{font-size:13px;padding:3px 6px;background-color:#fff;border-left:1px dotted #999}.c3-tooltip td>span{display:inline-block;width:10px;height:10px;margin-right:6px}.c3-tooltip td.value{text-align:right}.c3-area{stroke-width:0;opacity:.2}.c3-chart-arcs .c3-chart-arcs-background{fill:#e0e0e0;stroke:none}.c3-chart-arcs .c3-chart-arcs-gauge-unit{fill:#000;font-size:16px}.c3-chart-arcs .c3-chart-arcs-gauge-max,.c3-chart-arcs .c3-chart-arcs-gauge-min{fill:#777}.c3-chart-arc .c3-gauge-value{fill:#000}
.c3 svg{font:10px sans-serif}.c3 line,.c3 path{fill:none;stroke:#000}.c3 text{-webkit-user-select:none;-moz-user-select:none;user-select:none}.c3-bars path,.c3-event-rect,.c3-legend-item-tile,.c3-xgrid-focus,.c3-ygrid{shape-rendering:crispEdges}.c3-chart-arc path{stroke:#fff}.c3-chart-arc text{fill:#fff;font-size:13px}.c3-grid line{stroke:#aaa}.c3-grid text{fill:#aaa}.c3-xgrid,.c3-ygrid{stroke-dasharray:3 3}.c3-text.c3-empty{fill:gray;font-size:2em}.c3-line{stroke-width:1px}.c3-circle._expanded_{stroke-width:1px;stroke:#fff}.c3-selected-circle{fill:#fff;stroke-width:2px}.c3-bar{stroke-width:0}.c3-bar._expanded_{fill-opacity:.75}.c3-chart-arcs-title{dominant-baseline:middle;font-size:1.3em}.c3-target.c3-focused{opacity:1}.c3-target.c3-focused path.c3-line,.c3-target.c3-focused path.c3-step{stroke-width:2px}.c3-target.c3-defocused{opacity:.3!important}.c3-region{fill:#4682b4;fill-opacity:.1}.c3-brush .extent{fill-opacity:.1}.c3-legend-item{font-size:12px}.c3-legend-item-hidden{opacity:.15}.c3-legend-background{opacity:.75;fill:#fff;stroke:#d3d3d3;stroke-width:1}.c3-tooltip-container{z-index:10}.c3-tooltip{border-collapse:collapse;border-spacing:0;background-color:#fff;empty-cells:show;width:auto;-webkit-box-shadow:7px 7px 12px -9px #777;-moz-box-shadow:7px 7px 12px -9px #777;box-shadow:7px 7px 12px -9px #777;opacity:.9}.c3-tooltip tr{border:1px solid #CCC}.c3-tooltip th{background-color:#aaa;font-size:14px;padding:2px 5px;text-align:left;color:#FFF}.c3-tooltip td{font-size:13px;padding:3px 6px;background-color:#fff;border-left:1px dotted #999;color:#000}.c3-tooltip td>span{display:inline-block;width:10px;height:10px;margin-right:6px}.c3-tooltip td.value{text-align:right}.c3-area{stroke-width:0;opacity:.2}.c3-chart-arcs .c3-chart-arcs-background{fill:#e0e0e0;stroke:none}.c3-chart-arcs .c3-chart-arcs-gauge-unit{fill:#000;font-size:16px}.c3-chart-arcs .c3-chart-arcs-gauge-max,.c3-chart-arcs .c3-chart-arcs-gauge-min{fill:#777}.c3-chart-arc .c3-gauge-value{fill:#000}

10
c3.min.js vendored

File diff suppressed because one or more lines are too long

4
component.json

@ -2,10 +2,10 @@
"name": "c3",
"repo": "masayuki0812/c3",
"description": "A D3-based reusable chart library",
"version": "0.4.8",
"version": "0.4.9",
"keywords": [],
"dependencies": {
"mbostock/d3": "v3.4.4"
"mbostock/d3": "v3.5.0"
},
"development": {},
"license": "MIT",

8
package.json

@ -1,6 +1,6 @@
{
"name": "c3",
"version": "0.4.8",
"version": "0.4.9",
"description": "D3-based reusable chart library",
"main": "c3.js",
"scripts": {
@ -20,17 +20,17 @@
"gitHead": "84e03109d9a590f9c8ef687c03d751f666080c6f",
"readmeFilename": "README.md",
"dependencies": {
"d3": "~3.4.4"
"d3": "<=3.5.0"
},
"devDependencies": {
"grunt": "^0.4.5",
"grunt-contrib-concat": "~0.5.0",
"grunt-contrib-cssmin": "^0.10.0",
"grunt-contrib-jasmine": "~0.8.0",
"grunt-contrib-jshint": "~0.7.1",
"grunt-contrib-sass": "^0.8.1",
"grunt-contrib-jshint": "~0.10.0",
"grunt-contrib-uglify": "~0.4.0",
"grunt-contrib-watch": "^0.6.1",
"grunt-sass": "^0.17.0",
"load-grunt-tasks": "~0.2.0"
}
}

4
spec/api.data-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 api data', function () {
'use strict';

4
spec/api.focus-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 api load', function () {
'use strict';

4
spec/api.grid-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 api grid', function () {
'use strict';

4
spec/api.load-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 api load', function () {
'use strict';

4
spec/api.zoom-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 api zoom', function () {
'use strict';

4
spec/arc-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart axis', function () {
'use strict';

13
spec/axis-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart axis', function () {
'use strict';
@ -380,11 +376,10 @@ describe('c3 chart axis', function () {
expectedTickTexts = [
'this is a very',
'long tick text',
'on category',
'axis',
'on category axis'
],
expectedX = '0';
expect(tspans.size()).toBe(4);
expect(tspans.size()).toBe(3);
tspans.each(function (d, i) {
var tspan = d3.select(this);
expect(tspan.text()).toBe(expectedTickTexts[i]);
@ -697,7 +692,7 @@ describe('c3 chart axis', function () {
it('should not have inner y axis', function () {
var paddingLeft = chart.internal.getCurrentPaddingLeft(),
tickTexts = chart.internal.main.selectAll('.c3-axis-y g.tick text');
expect(paddingLeft).toBe(50);
expect(paddingLeft).toBeGreaterThan(19);
tickTexts.each(function () {
expect(+d3.select(this).attr('x')).toBeLessThan(0);
});
@ -742,7 +737,7 @@ describe('c3 chart axis', function () {
it('should not have inner y axis', function () {
var paddingRight = chart.internal.getCurrentPaddingRight(),
tickTexts = chart.internal.main.selectAll('.c3-axis-2y g.tick text');
expect(paddingRight).toBeGreaterThan(39);
expect(paddingRight).toBeGreaterThan(19);
tickTexts.each(function () {
expect(+d3.select(this).attr('x')).toBeGreaterThan(0);
});

3
spec/c3-spec.js

@ -1,6 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it;
describe('c3', function () {
'use strict';

4
spec/class-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart class', function () {
'use strict';

4
spec/core-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart', function () {
'use strict';

120
spec/data-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart data', function () {
'use strict';
@ -173,10 +169,10 @@ describe('c3 chart data', function () {
it('should have Date object as x', function () {
var xs = chart.internal.data.xs;
expect(+xs.data1[0]).toBe(+new Date(2014, 11, 3, 16, 1, 1, 123));
expect(+xs.data1[1]).toBe(+new Date(2014, 11, 3, 16, 2, 2, 345));
expect(+xs.data2[0]).toBe(+new Date(2014, 11, 3, 16, 1, 1, 123));
expect(+xs.data2[1]).toBe(+new Date(2014, 11, 3, 16, 2, 2, 345));
expect(+xs.data1[0]).toBe(1417622461123);
expect(+xs.data1[1]).toBe(1417622522345);
expect(+xs.data2[0]).toBe(1417622461123);
expect(+xs.data2[1]).toBe(1417622522345);
});
});
@ -213,10 +209,10 @@ describe('c3 chart data', function () {
it('should have Date object as x', function () {
var xs = chart.internal.data.xs;
expect(+xs.data1[0]).toBe(+new Date(2014, 11, 3, 16, 1, 1, 123));
expect(+xs.data1[1]).toBe(+new Date(2014, 11, 3, 16, 2, 2, 345));
expect(+xs.data2[0]).toBe(+new Date(2014, 11, 3, 16, 1, 1, 123));
expect(+xs.data2[1]).toBe(+new Date(2014, 11, 3, 16, 2, 2, 345));
expect(+xs.data1[0]).toBe(1417622461123);
expect(+xs.data1[1]).toBe(1417622522345);
expect(+xs.data2[0]).toBe(1417622461123);
expect(+xs.data2[1]).toBe(1417622522345);
});
});
@ -227,6 +223,106 @@ describe('c3 chart data', function () {
describe('data.label', function () {
describe('for all targets', function () {
it('should update args to show data label for all data', function () {
args = {
data: {
columns: [
['data1', 100, 200, 100, 400, 150, 250],
['data2', 10, 20, 10, 40, 15, 25],
['data3', 1000, 2000, 1000, 4000, 1500, 2500]
],
labels: true
}
};
expect(true).toBeTruthy();
});
it('should have data labels on all data', function () {
d3.selectAll('.c3-texts-data1 text').each(function (d, i) {
expect(d3.select(this).text()).toBe(args.data.columns[0][i + 1] + '');
});
d3.selectAll('.c3-texts-data2 text').each(function (d, i) {
expect(d3.select(this).text()).toBe(args.data.columns[1][i + 1] + '');
});
d3.selectAll('.c3-texts-data3 text').each(function (d, i) {
expect(d3.select(this).text()).toBe(args.data.columns[2][i + 1] + '');
});
});
});
describe('for each target', function () {
describe('as true', function () {
it('should update args to show data label for only data1', function () {
args = {
data: {
columns: [
['data1', 100, 200, 100, 400, 150, 250],
['data2', 10, 20, 10, 40, 15, 25],
['data3', 1000, 2000, 1000, 4000, 1500, 2500]
],
labels: {
format: {
data1: true
}
}
}
};
expect(true).toBeTruthy();
});
it('should have data labels on all data', function () {
d3.selectAll('.c3-texts-data1 text').each(function (d, i) {
expect(d3.select(this).text()).toBe(args.data.columns[0][i + 1] + '');
});
d3.selectAll('.c3-texts-data2 text').each(function () {
expect(d3.select(this).text()).toBe('');
});
d3.selectAll('.c3-texts-data3 text').each(function () {
expect(d3.select(this).text()).toBe('');
});
});
});
describe('as function', function () {
it('should update args to show data label for only data1', function () {
args = {
data: {
columns: [
['data1', 100, 200, 100, 400, 150, 250],
['data2', 10, 20, 10, 40, 15, 25],
['data3', 1000, 2000, 1000, 4000, 1500, 2500]
],
labels: {
format: {
data1: d3.format('$')
}
}
}
};
expect(true).toBeTruthy();
});
it('should have data labels on all data', function () {
d3.selectAll('.c3-texts-data1 text').each(function (d, i) {
expect(d3.select(this).text()).toBe('$' + args.data.columns[0][i + 1]);
});
d3.selectAll('.c3-texts-data2 text').each(function () {
expect(d3.select(this).text()).toBe('');
});
d3.selectAll('.c3-texts-data3 text').each(function () {
expect(d3.select(this).text()).toBe('');
});
});
});
});
describe('with small values', function () {
it('should update args to show data label', function () {

6
spec/domain-spec.js

@ -1,9 +1,5 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart axis', function () {
describe('c3 chart domain', function () {
'use strict';
var chart, d3;

44
spec/grid-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart grid', function () {
'use strict';
@ -83,6 +79,44 @@ describe('c3 chart grid', function () {
describe('x grid lines', function () {
describe('with padding.top', function () {
it('should have correct height', function () {
args = {
data: {
columns: [
['data1', 30, 200, 100, 400],
]
},
grid: {
x: {
lines: [
{value: 3, text: 'Label 3'}
]
}
},
padding: {
top: 50
}
};
expect(true).toBeTruthy();
});
it('should show x grid lines', function () {
var lines = chart.internal.main.select('.c3-xgrid-lines .c3-xgrid-line'),
expectedX1 = 593,
expectedText = ['Label 3'];
lines.each(function (id, i) {
var line = d3.select(this),
l = line.select('line'),
t = line.select('text');
expect(+l.attr('x1')).toBeCloseTo(expectedX1, -2);
expect(t.text()).toBe(expectedText[i]);
});
});
});
describe('on category axis', function () {
it('should update args', function () {
@ -119,7 +153,7 @@ describe('c3 chart grid', function () {
var line = d3.select(this),
l = line.select('line'),
t = line.select('text');
expect(+l.attr('x1')).toBeCloseTo(expectedX1[i], -1);
expect(+l.attr('x1')).toBeCloseTo(expectedX1[i], -2);
expect(t.text()).toBe(expectedText[i]);
});
});

20
spec/interaction-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart interaction', function () {
'use strict';
@ -46,8 +42,8 @@ describe('c3 chart interaction', function () {
widths = [60, 67.5, 202, 194];
d3.selectAll('.c3-event-rect').each(function (d, i) {
var box = d3.select(this).node().getBoundingClientRect();
expect(box.left).toBe(lefts[i]);
expect(box.width).toBe(widths[i]);
expect(box.left).toBeCloseTo(lefts[i], -2);
expect(box.width).toBeCloseTo(widths[i], -2);
});
});
@ -70,8 +66,8 @@ describe('c3 chart interaction', function () {
expect(eventRects.size()).toBe(1);
eventRects.each(function () {
var box = d3.select(this).node().getBoundingClientRect();
expect(box.left).toBe(40.5);
expect(box.width).toBe(598);
expect(box.left).toBeCloseTo(40.5, -2);
expect(box.width).toBeCloseTo(598, -2);
});
});
});
@ -96,8 +92,8 @@ describe('c3 chart interaction', function () {
widths = [149.5, 160, 147, 136];
d3.selectAll('.c3-event-rect').each(function (d, i) {
var box = d3.select(this).node().getBoundingClientRect();
expect(box.left).toBe(lefts[i]);
expect(box.width).toBe(widths[i]);
expect(box.left).toBeCloseTo(lefts[i], -2);
expect(box.width).toBeCloseTo(widths[i], -2);
});
});
@ -120,8 +116,8 @@ describe('c3 chart interaction', function () {
expect(eventRects.size()).toBe(1);
eventRects.each(function () {
var box = d3.select(this).node().getBoundingClientRect();
expect(box.left).toBe(40.5);
expect(box.width).toBe(598);
expect(box.left).toBeCloseTo(40.5, -2);
expect(box.width).toBeCloseTo(598, -2);
});
});

6
spec/legend-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart legend', function () {
'use strict';
@ -56,7 +52,7 @@ describe('c3 chart legend', function () {
it('should be positioned properly', function () {
var box = d3.select('.c3-legend-background').node().getBoundingClientRect();
expect(box.top).toBe(5.5);
expect(box.left).toBe(60.5);
expect(box.left).toBeGreaterThan(30);
});
it('should have automatically calculated height', function () {

4
spec/shape.bar-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
var setMouseEvent = window.setMouseEvent;

4
spec/shape.line-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart shape line', function () {
'use strict';

60
spec/tooltip-spec.js

@ -1,29 +1,34 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
var jasmine = window.jasmine,
beforeAll = window.beforeAll;
describe('c3 chart tooltip', function () {
'use strict';
var chart, d3;
var tooltipConfiguration;
var args = {
var args = function () {
return {
data: {
columns: [
['data1', 30, 200, 100, 400, 150, 250],
['data2', 50, 20, 10, 40, 15, 25],
['data3', 150, 120, 110, 140, 115, 125]
]
}
],
},
tooltip: tooltipConfiguration
};
};
beforeEach(function (done) {
chart = window.initChart(chart, args, done);
chart = window.initChart(chart, args(), done);
d3 = chart.internal.d3;
});
describe('tooltip position', function () {
beforeAll(function () {
tooltipConfiguration = {};
});
describe('without left margin', function () {
@ -35,9 +40,9 @@ describe('c3 chart tooltip', function () {
top = Math.floor(+tooltipContainer.style('top').replace(/px/, '')),
left = Math.floor(+tooltipContainer.style('left').replace(/px/, '')),
topExpected = 115,
leftExpected = 307;
leftExpected = 280;
expect(top).toBe(topExpected);
expect(left).toBe(leftExpected);
expect(left).toBeGreaterThan(leftExpected);
});
});
@ -57,13 +62,44 @@ describe('c3 chart tooltip', function () {
top = Math.floor(+tooltipContainer.style('top').replace(/px/, '')),
left = Math.floor(+tooltipContainer.style('left').replace(/px/, '')),
topExpected = 115,
leftExpected = 307;
leftExpected = 280;
expect(top).toBe(topExpected);
expect(left).toBe(leftExpected);
expect(left).toBeGreaterThan(leftExpected);
});
});
});
describe('tooltip positionFunction', function () {
var topExpected = 37, leftExpected = 79;
beforeAll(function () {
tooltipConfiguration = {
position: function (data, width, height, element) {
expect(data.length).toBe(args().data.columns.length);
expect(data[0]).toEqual(jasmine.objectContaining({
index: 2,
value: 100,
id: 'data1'
}));
expect(width).toBeGreaterThan(0);
expect(height).toBeGreaterThan(0);
expect(element).toBe(d3.select('.c3-event-rect-2').node());
return {top: topExpected, left: leftExpected};
}
};
});
it('should be set to the coordinate where the function returned', function () {
var eventRect = d3.select('.c3-event-rect-2').node();
window.setMouseEvent(chart, 'mousemove', 100, 100, eventRect);
var tooltipContainer = d3.select('.c3-tooltip-container'),
top = Math.floor(+tooltipContainer.style('top').replace(/px/, '')),
left = Math.floor(+tooltipContainer.style('left').replace(/px/, ''));
expect(top).toBe(topExpected);
expect(left).toBe(leftExpected);
});
});
});

4
spec/type-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart types', function () {
'use strict';

4
spec/zoom-spec.js

@ -1,7 +1,3 @@
var describe = window.describe,
expect = window.expect,
it = window.it,
beforeEach = window.beforeEach;
describe('c3 chart zoom', function () {
'use strict';

13
src/api.chart.js

@ -12,9 +12,16 @@ c3_chart_fn.flush = function () {
c3_chart_fn.destroy = function () {
var $$ = this.internal;
$$.data.targets = undefined;
$$.data.xs = {};
$$.selectChart.classed('c3', false).html("");
window.clearInterval($$.intervalForObserveInserted);
window.onresize = null;
$$.selectChart.classed('c3', false).html("");
// MEMO: this is needed because the reference of some elements will not be released, then memory leak will happen.
Object.keys($$).forEach(function (key) {
$$[key] = null;
});
return null;
};

4
src/api.show.js

@ -42,9 +42,9 @@ c3_chart_fn.hide = function (targetIds, options) {
$$.redraw({withUpdateOrgXDomain: true, withUpdateXDomain: true, withLegend: true});
};
c3_chart_fn.toggle = function (targetIds) {
c3_chart_fn.toggle = function (targetIds, options) {
var that = this, $$ = this.internal;
$$.mapToTargetIds(targetIds).forEach(function (targetId) {
$$.isTargetToShow(targetId) ? that.hide(targetId) : that.show(targetId);
$$.isTargetToShow(targetId) ? that.hide(targetId, options) : that.show(targetId, options);
});
};

1
src/api.transform.js

@ -11,5 +11,6 @@ c3_chart_internal_fn.transformTo = function (targetIds, type, optionsForRedraw)
options.withTransitionForTransform = false;
$$.transiting = false;
$$.setTargetType(targetIds, type);
$$.updateTargets($$.data.targets); // this is needed when transforming to arc
$$.updateAndRedraw(options);
};

2
src/arc.js

@ -273,7 +273,7 @@ c3_chart_internal_fn.redrawArc = function (duration, durationForExit, withTransf
var updated = $$.updateAngle(d),
arcData = $$.convertToArcData(updated),
selectedData = [arcData];
$$.showTooltip(selectedData, d3.mouse(this));
$$.showTooltip(selectedData, this);
} : null)
.on('mouseout', config.interaction_enabled ? function (d) {
var updated, arcData;

34
src/axis.js

@ -30,13 +30,14 @@ c3_chart_internal_fn.initAxis = function () {
.attr("transform", config.axis_rotated ? "" : "rotate(-90)")
.style("text-anchor", $$.textAnchorForY2AxisLabel.bind($$));
};
c3_chart_internal_fn.getXAxis = function (scale, orient, tickFormat, tickValues, withOuterTick) {
c3_chart_internal_fn.getXAxis = function (scale, orient, tickFormat, tickValues, withOuterTick, withoutTransition) {
var $$ = this, config = $$.config,
axisParams = {
isCategory: $$.isCategorized(),
withOuterTick: withOuterTick,
tickMultiline: config.axis_x_tick_multiline,
tickWidth: config.axis_x_tick_width
tickWidth: config.axis_x_tick_width,
withoutTransition: withoutTransition,
},
axis = c3_axis($$.d3, axisParams).scale(scale).orient(orient);
@ -63,6 +64,19 @@ c3_chart_internal_fn.getXAxis = function (scale, orient, tickFormat, tickValues,
return axis;
};
c3_chart_internal_fn.updateXAxisTickValues = function (targets, axis) {
var $$ = this, config = $$.config, tickValues;
if (config.axis_x_tick_fit || config.axis_x_tick_count) {
tickValues = $$.generateTickValues($$.mapTargetsToUniqueXs(targets), config.axis_x_tick_count, $$.isTimeSeries());
}
if (axis) {
axis.tickValues(tickValues);
} else {
$$.xAxis.tickValues(tickValues);
$$.subXAxis.tickValues(tickValues);
}
return tickValues;
};
c3_chart_internal_fn.getYAxis = function (scale, orient, tickFormat, tickValues, withOuterTick) {
var axisParams = {withOuterTick: withOuterTick},
axis = c3_axis(this.d3, axisParams).scale(scale).orient(orient).tickFormat(tickFormat);
@ -266,7 +280,7 @@ c3_chart_internal_fn.rotateTickText = function (axis, transition, rotate) {
c3_chart_internal_fn.getMaxTickWidth = function (id, withoutRecompute) {
var $$ = this, config = $$.config,
maxWidth = 0, targetsToShow, scale, axis;
maxWidth = 0, targetsToShow, scale, axis, body, svg;
if (withoutRecompute && $$.currentMaxTickWidths[id]) {
return $$.currentMaxTickWidths[id];
}
@ -281,13 +295,21 @@ c3_chart_internal_fn.getMaxTickWidth = function (id, withoutRecompute) {
} else {
scale = $$.x.copy().domain($$.getXDomain(targetsToShow));
axis = $$.getXAxis(scale, $$.xOrient, $$.xAxisTickFormat, $$.xAxisTickValues);
$$.updateXAxisTickValues(targetsToShow, axis);
}
$$.d3.select('body').append("g").style('visibility', 'hidden').call(axis).each(function () {
body = this.d3.select('body').classed('c3', true);
svg = body.append('svg').style('visibility', 'hidden');
svg.append('g').call(axis).each(function () {
$$.d3.select(this).selectAll('text tspan').each(function () {
var box = this.getBoundingClientRect();
if (box.left > 0 && maxWidth < box.width) { maxWidth = box.width; }
if (box.left >= 0 && maxWidth < box.width) { maxWidth = box.width; }
});
});
}).remove();
// TODO: time lag to get maxWidth
window.setTimeout(function () {
svg.remove();
}, 100);
body.classed('c3', false);
}
$$.currentMaxTickWidths[id] = maxWidth <= 0 ? $$.currentMaxTickWidths[id] : maxWidth;
return $$.currentMaxTickWidths[id];

3
src/c3.axis.js

@ -48,7 +48,8 @@ function c3_axis(d3, params) {
return newScale;
}
function textFormatted(v) {
return tickFormat ? tickFormat(v) : v;
var formatted = tickFormat ? tickFormat(v) : v;
return typeof formatted !== 'undefined' ? formatted : '';
}
function getSizeFor1Char(tick) {
if (tickTextCharSize) {

2
src/color.js

@ -6,7 +6,7 @@ c3_chart_internal_fn.generateColor = function () {
ids = [];
return function (d) {
var id = d.id || d, color;
var id = d.id || (d.data && d.data.id) || d, color;
// if callback function is provided
if (colors[id] instanceof Function) {

7
src/config.js

@ -20,6 +20,7 @@ c3_chart_internal_fn.getDefaultConfig = function () {
onresize: function () {},
onresized: function () {},
oninit: function () {},
onrendered: function () {},
transition_duration: 350,
data_x: undefined,
data_xs: {},
@ -44,13 +45,12 @@ c3_chart_internal_fn.getDefaultConfig = function () {
data_selection_grouped: false,
data_selection_isselectable: function () { return true; },
data_selection_multiple: true,
data_selection_draggable: false,
data_onclick: function () {},
data_onmouseover: function () {},
data_onmouseout: function () {},
data_onselected: function () {},
data_onunselected: function () {},
data_ondragstart: function () {},
data_ondragend: function () {},
data_url: undefined,
data_json: undefined,
data_rows: undefined,
@ -105,6 +105,7 @@ c3_chart_internal_fn.getDefaultConfig = function () {
axis_y_type: undefined,
axis_y_max: undefined,
axis_y_min: undefined,
axis_y_inverted: false,
axis_y_center: undefined,
axis_y_inner: undefined,
axis_y_label: {},
@ -119,6 +120,7 @@ c3_chart_internal_fn.getDefaultConfig = function () {
axis_y2_show: false,
axis_y2_max: undefined,
axis_y2_min: undefined,
axis_y2_inverted: false,
axis_y2_center: undefined,
axis_y2_inner: undefined,
axis_y2_label: {},
@ -183,6 +185,7 @@ c3_chart_internal_fn.getDefaultConfig = function () {
tooltip_format_title: undefined,
tooltip_format_name: undefined,
tooltip_format_value: undefined,
tooltip_position: undefined,
tooltip_contents: function (d, defaultTitleFormat, defaultValueFormat, color) {
return this.getTooltipContent ? this.getTooltipContent(d, defaultTitleFormat, defaultValueFormat, color) : '';
},

119
src/core.js

@ -1,4 +1,4 @@
var c3 = { version: "0.4.8" };
var c3 = { version: "0.4.9" };
var c3_chart_fn, c3_chart_internal_fn;
@ -394,7 +394,7 @@ c3_chart_internal_fn.updateSizes = function () {
};
c3_chart_internal_fn.updateTargets = function (targets) {
var $$ = this, config = $$.config;
var $$ = this;
/*-- Main --*/
@ -408,14 +408,19 @@ c3_chart_internal_fn.updateTargets = function (targets) {
$$.updateTargetsForLine(targets);
//-- Arc --//
if ($$.updateTargetsForArc) { $$.updateTargetsForArc(targets); }
if ($$.updateTargetsForSubchart) { $$.updateTargetsForSubchart(targets); }
if ($$.hasArcType() && $$.updateTargetsForArc) { $$.updateTargetsForArc(targets); }
/*-- Show --*/
/*-- Sub --*/
if ($$.updateTargetsForSubchart) { $$.updateTargetsForSubchart(targets); }
// Fade-in each chart
$$.showTargets();
};
c3_chart_internal_fn.showTargets = function () {
var $$ = this;
$$.svg.selectAll('.' + CLASS.target).filter(function (d) { return $$.isTargetToShow(d.id); })
.transition().duration(config.transition_duration)
.transition().duration($$.config.transition_duration)
.style("opacity", 1);
};
@ -470,13 +475,7 @@ c3_chart_internal_fn.redraw = function (options, transitions) {
if (targetsToShow.length) {
$$.updateXDomain(targetsToShow, withUpdateXDomain, withUpdateOrgXDomain, withTrimXDomain);
if (!config.axis_x_tick_values) {
if (config.axis_x_tick_fit || config.axis_x_tick_count) {
tickValues = $$.generateTickValues($$.mapTargetsToUniqueXs(targetsToShow), config.axis_x_tick_count, $$.isTimeSeries());
} else {
tickValues = undefined;
}
$$.xAxis.tickValues(tickValues);
$$.subXAxis.tickValues(tickValues);
tickValues = $$.updateXAxisTickValues(targetsToShow);
}
} else {
$$.xAxis.tickValues([]);
@ -551,22 +550,22 @@ c3_chart_internal_fn.redraw = function (options, transitions) {
.style('opacity', targetsToShow.length ? 0 : 1);
// grid
$$.redrawGrid(duration);
$$.updateGrid(duration);
// rect for regions
$$.redrawRegion(duration);
$$.updateRegion(duration);
// bars
$$.redrawBar(durationForExit);
$$.updateBar(durationForExit);
// lines, areas and cricles
$$.redrawLine(durationForExit);
$$.redrawArea(durationForExit);
$$.redrawCircle();
$$.updateLine(durationForExit);
$$.updateArea(durationForExit);
$$.updateCircle();
// text
if ($$.hasDataLabel()) {
$$.redrawText(durationForExit);
$$.updateText(durationForExit);
}
// arc
@ -596,24 +595,7 @@ c3_chart_internal_fn.redraw = function (options, transitions) {
cx = ($$.config.axis_rotated ? $$.circleY : $$.circleX).bind($$);
cy = ($$.config.axis_rotated ? $$.circleX : $$.circleY).bind($$);
// transition should be derived from one transition
d3.transition().duration(duration).each(function () {
var transitions = [];
$$.addTransitionForBar(transitions, drawBar);
$$.addTransitionForLine(transitions, drawLine);
$$.addTransitionForArea(transitions, drawArea);
$$.addTransitionForCircle(transitions, cx, cy);
$$.addTransitionForText(transitions, xForText, yForText, options.flow);
$$.addTransitionForRegion(transitions);
$$.addTransitionForGrid(transitions);
// Wait for end of transitions if called from flow API
if (options.flow) {
waitForDraw = $$.generateWait();
transitions.forEach(function (t) {
waitForDraw.add(t);
});
flow = $$.generateFlow({
targets: targetsToShow,
flow: options.flow,
@ -628,8 +610,54 @@ c3_chart_internal_fn.redraw = function (options, transitions) {
yForText: yForText
});
}
if (duration && $$.isTabVisible()) { // Only use transition if tab visible. See #938.
// transition should be derived from one transition
d3.transition().duration(duration).each(function () {
var transitionsToWait = [];
// redraw and gather transitions
[
$$.redrawBar(drawBar, true),
$$.redrawLine(drawLine, true),
$$.redrawArea(drawArea, true),
$$.redrawCircle(cx, cy, true),
$$.redrawText(xForText, yForText, options.flow, true),
$$.redrawRegion(true),
$$.redrawGrid(true),
].forEach(function (transitions) {
transitions.forEach(function (transition) {
transitionsToWait.push(transition);
});
});
// Wait for end of transitions to call flow and onrendered callback
waitForDraw = $$.generateWait();
transitionsToWait.forEach(function (t) {
waitForDraw.add(t);
});
})
.call(waitForDraw || function () {}, flow || function () {});
.call(waitForDraw, function () {
if (flow) {
flow();
}
if (config.onrendered) {
config.onrendered.call($$);
}
});
}
else {
$$.redrawBar(drawBar);
$$.redrawLine(drawLine);
$$.redrawArea(drawArea);
$$.redrawCircle(cx, cy);
$$.redrawText(xForText, yForText, options.flow);
$$.redrawRegion();
$$.redrawGrid();
if (config.onrendered) {
config.onrendered.call($$);
}
}
// update fadein condition
$$.mapToIds($$.data.targets).forEach(function (id) {
@ -923,3 +951,18 @@ c3_chart_internal_fn.parseDate = function (date) {
}
return parsedDate;
};
c3_chart_internal_fn.isTabVisible = function () {
var hidden;
if (typeof document.hidden !== "undefined") { // Opera 12.10 and Firefox 18 and later support
hidden = "hidden";
} else if (typeof document.mozHidden !== "undefined") {
hidden = "mozHidden";
} else if (typeof document.msHidden !== "undefined") {
hidden = "msHidden";
} else if (typeof document.webkitHidden !== "undefined") {
hidden = "webkitHidden";
}
return document[hidden] ? false : true;
};

4
src/data.js

@ -261,13 +261,13 @@ c3_chart_internal_fn.hasDataLabel = function () {
}
return false;
};
c3_chart_internal_fn.getDataLabelLength = function (min, max, axisId, key) {
c3_chart_internal_fn.getDataLabelLength = function (min, max, key) {
var $$ = this,
lengths = [0, 0], paddingCoef = 1.3;
$$.selectChart.select('svg').selectAll('.dummy')
.data([min, max])
.enter().append('text')
.text(function (d) { return $$.formatByAxisId(axisId)(d); })
.text(function (d) { return $$.dataLabelFormat(d.id)(d); })
.each(function (d, i) {
lengths[i] = this.getBoundingClientRect()[key] * paddingCoef;
})

24
src/domain.js

@ -66,22 +66,19 @@ c3_chart_internal_fn.getYDomain = function (targets, axisId, xDomain) {
yTargets = xDomain ? $$.filterByXDomain(targetsByAxisId, xDomain) : targetsByAxisId,
yMin = axisId === 'y2' ? config.axis_y2_min : config.axis_y_min,
yMax = axisId === 'y2' ? config.axis_y2_max : config.axis_y_max,
yDomainMin = isValue(yMin) ? yMin : $$.getYDomainMin(yTargets),
yDomainMax = isValue(yMax) ? yMax : $$.getYDomainMax(yTargets),
domainLength, padding, padding_top, padding_bottom,
yDomainMin = $$.getYDomainMin(yTargets),
yDomainMax = $$.getYDomainMax(yTargets),
domain, domainLength, padding, padding_top, padding_bottom,
center = axisId === 'y2' ? config.axis_y2_center : config.axis_y_center,
yDomainAbs, lengths, diff, ratio, isAllPositive, isAllNegative,
isZeroBased = ($$.hasType('bar', yTargets) && config.bar_zerobased) || ($$.hasType('area', yTargets) && config.area_zerobased),
isInverted = axisId === 'y2' ? config.axis_y2_inverted : config.axis_y_inverted,
showHorizontalDataLabel = $$.hasDataLabel() && config.axis_rotated,
showVerticalDataLabel = $$.hasDataLabel() && !config.axis_rotated;
if (yDomainMax < yDomainMin) {
if (isValue(yMin)) {
yDomainMax = yDomainMin + 10; // TODO: introduce axis.y.maxMin
} else {
yDomainMin = yDomainMax - 10; // TODO: introduce axis.y.minMax
}
}
// MEMO: avoid inverting domain unexpectedly
yDomainMin = isValue(yMin) ? yMin : isValue(yMax) ? (yDomainMin < yMax ? yDomainMin : yMax - 10) : yDomainMin;
yDomainMax = isValue(yMax) ? yMax : isValue(yMin) ? (yMin < yDomainMax ? yDomainMax : yMin + 10) : yDomainMax;
if (yTargets.length === 0) { // use current domain if target of axisId is none
return axisId === 'y2' ? $$.y2.domain() : $$.y.domain();
@ -119,13 +116,13 @@ c3_chart_internal_fn.getYDomain = function (targets, axisId, xDomain) {
}
// add padding for data label
if (showHorizontalDataLabel) {
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, axisId, 'width');
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, 'width');
diff = diffDomain($$.y.range());
ratio = [lengths[0] / diff, lengths[1] / diff];
padding_top += domainLength * (ratio[1] / (1 - ratio[0] - ratio[1]));
padding_bottom += domainLength * (ratio[0] / (1 - ratio[0] - ratio[1]));
} else if (showVerticalDataLabel) {
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, axisId, 'height');
lengths = $$.getDataLabelLength(yDomainMin, yDomainMax, 'height');
padding_top += this.convertPixelsToAxisPadding(lengths[1], domainLength);
padding_bottom += this.convertPixelsToAxisPadding(lengths[0], domainLength);
}
@ -142,7 +139,8 @@ c3_chart_internal_fn.getYDomain = function (targets, axisId, xDomain) {
if (isAllPositive) { padding_bottom = yDomainMin; }
if (isAllNegative) { padding_top = -yDomainMax; }
}
return [yDomainMin - padding_bottom, yDomainMax + padding_top];
domain = [yDomainMin - padding_bottom, yDomainMax + padding_top];
return isInverted ? domain.reverse() : domain;
};
c3_chart_internal_fn.getXDomainMin = function (targets) {
var $$ = this, config = $$.config;

3
src/drag.js

@ -65,7 +65,6 @@ c3_chart_internal_fn.dragstart = function (mouse) {
.attr('class', CLASS.dragarea)
.style('opacity', 0.1);
$$.dragging = true;
$$.config.data_ondragstart.call($$.api);
};
c3_chart_internal_fn.dragend = function () {
@ -79,6 +78,4 @@ c3_chart_internal_fn.dragend = function () {
$$.main.selectAll('.' + CLASS.shape)
.classed(CLASS.INCLUDED, false);
$$.dragging = false;
$$.config.data_ondragend.call($$.api);
};

12
src/format.js

@ -23,16 +23,20 @@ c3_chart_internal_fn.defaultValueFormat = function (v) {
c3_chart_internal_fn.defaultArcValueFormat = function (v, ratio) {
return (ratio * 100).toFixed(1) + '%';
};
c3_chart_internal_fn.formatByAxisId = function (axisId) {
c3_chart_internal_fn.dataLabelFormat = function (targetId) {
var $$ = this, data_labels = $$.config.data_labels,
format = function (v) { return isValue(v) ? +v : ""; };
format, defaultFormat = function (v) { return isValue(v) ? +v : ""; };
// find format according to axis id
if (typeof data_labels.format === 'function') {
format = data_labels.format;
} else if (typeof data_labels.format === 'object') {
if (data_labels.format[axisId]) {
format = data_labels.format[axisId];
if (data_labels.format[targetId]) {
format = data_labels.format[targetId] === true ? defaultFormat : data_labels.format[targetId];
} else {
format = function () { return ''; };
}
} else {
format = defaultFormat;
}
return format;
};

22
src/grid.js

@ -70,7 +70,7 @@ c3_chart_internal_fn.updateYGrid = function () {
};
c3_chart_internal_fn.redrawGrid = function (duration) {
c3_chart_internal_fn.updateGrid = function (duration) {
var $$ = this, main = $$.main, config = $$.config,
xgridLine, ygridLine, yv;
@ -91,7 +91,7 @@ c3_chart_internal_fn.redrawGrid = function (duration) {
xgridLine.append('text')
.attr("text-anchor", "end")
.attr("transform", config.axis_rotated ? "" : "rotate(-90)")
.attr('dx', config.axis_rotated ? 0 : -$$.margin.top)
.attr('dx', -4)
.attr('dy', -5)
.style("opacity", 0);
// udpate
@ -138,19 +138,23 @@ c3_chart_internal_fn.redrawGrid = function (duration) {
.style("opacity", 0)
.remove();
};
c3_chart_internal_fn.addTransitionForGrid = function (transitions) {
var $$ = this, config = $$.config, xv = $$.xv.bind($$);
transitions.push($$.xgridLines.select('line').transition()
c3_chart_internal_fn.redrawGrid = function (withTransition) {
var $$ = this, config = $$.config, xv = $$.xv.bind($$),
lines = $$.xgridLines.select('line'),
texts = $$.xgridLines.select('text');
return [
(withTransition ? lines.transition() : lines)
.attr("x1", config.axis_rotated ? 0 : xv)
.attr("x2", config.axis_rotated ? $$.width : xv)
.attr("y1", config.axis_rotated ? xv : $$.margin.top)
.attr("y1", config.axis_rotated ? xv : 0)
.attr("y2", config.axis_rotated ? xv : $$.height)
.style("opacity", 1));
transitions.push($$.xgridLines.select('text').transition()
.style("opacity", 1),
(withTransition ? texts.transition() : texts)
.attr("x", config.axis_rotated ? $$.width : 0)
.attr("y", xv)
.text(function (d) { return d.text; })
.style("opacity", 1));
.style("opacity", 1)
];
};
c3_chart_internal_fn.showXGridFocus = function (selectedData) {
var $$ = this, config = $$.config,

8
src/interaction.js

@ -175,7 +175,7 @@ c3_chart_internal_fn.generateEventRectsForSingleX = function (eventRectEnter) {
});
if (config.tooltip_grouped) {
$$.showTooltip(selectedData, d3.mouse(this));
$$.showTooltip(selectedData, this);
$$.showXGridFocus(selectedData);
}
@ -206,7 +206,7 @@ c3_chart_internal_fn.generateEventRectsForSingleX = function (eventRectEnter) {
eventRect.style('cursor', 'pointer');
}
if (!config.tooltip_grouped) {
$$.showTooltip([d], d3.mouse(this));
$$.showTooltip([d], this);
$$.showXGridFocus([d]);
if (config.point_focus_expand_enabled) { $$.expandCircles(index, d.id, true); }
$$.expandBars(index, d.id, true);
@ -231,10 +231,12 @@ c3_chart_internal_fn.generateEventRectsForSingleX = function (eventRectEnter) {
});
})
.call(
config.data_selection_draggable && $$.drag ? (
d3.behavior.drag().origin(Object)
.on('drag', function () { $$.drag(d3.mouse(this)); })
.on('dragstart', function () { $$.dragstart(d3.mouse(this)); })
.on('dragend', function () { $$.dragend(); })
) : function () {}
);
};
@ -289,7 +291,7 @@ c3_chart_internal_fn.generateEventRectsForMultipleXs = function (eventRectEnter)
selectedData = sameXData.map(function (d) {
return $$.addName(d);
});
$$.showTooltip(selectedData, mouse);
$$.showTooltip(selectedData, this);
// expand points
if (config.point_focus_expand_enabled) {

7
src/polyfill.js

@ -0,0 +1,7 @@
// fix problems using c3 with phantomjs #578
Function.prototype.bind = Function.prototype.bind || function (thisp) {
var fn = this;
return function () {
return fn.apply(thisp, arguments);
};
};

11
src/region.js

@ -4,7 +4,7 @@ c3_chart_internal_fn.initRegion = function () {
.attr("clip-path", $$.clipPath)
.attr("class", CLASS.regions);
};
c3_chart_internal_fn.redrawRegion = function (duration) {
c3_chart_internal_fn.updateRegion = function (duration) {
var $$ = this, config = $$.config;
// hide if arc type
@ -20,18 +20,21 @@ c3_chart_internal_fn.redrawRegion = function (duration) {
.style("opacity", 0)
.remove();
};
c3_chart_internal_fn.addTransitionForRegion = function (transitions) {
c3_chart_internal_fn.redrawRegion = function (withTransition) {
var $$ = this,
regions = $$.mainRegion.selectAll('rect'),
x = $$.regionX.bind($$),
y = $$.regionY.bind($$),
w = $$.regionWidth.bind($$),
h = $$.regionHeight.bind($$);
transitions.push($$.mainRegion.selectAll('rect').transition()
return [
(withTransition ? regions.transition() : regions)
.attr("x", x)
.attr("y", y)
.attr("width", w)
.attr("height", h)
.style("fill-opacity", function (d) { return isValue(d.opacity) ? d.opacity : 0.1; }));
.style("fill-opacity", function (d) { return isValue(d.opacity) ? d.opacity : 0.1; })
];
};
c3_chart_internal_fn.regionX = function (d) {
var $$ = this, config = $$.config,

13
src/shape.bar.js

@ -22,7 +22,7 @@ c3_chart_internal_fn.updateTargetsForBar = function (targets) {
.style("cursor", function (d) { return config.data_selection_isselectable(d) ? "pointer" : null; });
};
c3_chart_internal_fn.redrawBar = function (durationForExit) {
c3_chart_internal_fn.updateBar = function (durationForExit) {
var $$ = this,
barData = $$.barData.bind($$),
classBar = $$.classBar.bind($$),
@ -40,12 +40,13 @@ c3_chart_internal_fn.redrawBar = function (durationForExit) {
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForBar = function (transitions, drawBar) {
var $$ = this;
transitions.push($$.mainBar.transition()
c3_chart_internal_fn.redrawBar = function (drawBar, withTransition) {
return [
(withTransition ? this.mainBar.transition() : this.mainBar)
.attr('d', drawBar)
.style("fill", $$.color)
.style("opacity", 1));
.style("fill", this.color)
.style("opacity", 1)
];
};
c3_chart_internal_fn.getBarW = function (axis, barTargetsNum) {
var $$ = this, config = $$.config,

52
src/shape.line.js

@ -39,7 +39,7 @@ c3_chart_internal_fn.updateTargetsForLine = function (targets) {
// MEMO: can not keep same color...
//mainLineUpdate.exit().remove();
};
c3_chart_internal_fn.redrawLine = function (durationForExit) {
c3_chart_internal_fn.updateLine = function (durationForExit) {
var $$ = this;
$$.mainLine = $$.main.selectAll('.' + CLASS.lines).selectAll('.' + CLASS.line)
.data($$.lineData.bind($$));
@ -54,12 +54,13 @@ c3_chart_internal_fn.redrawLine = function (durationForExit) {
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForLine = function (transitions, drawLine) {
var $$ = this;
transitions.push($$.mainLine.transition()
c3_chart_internal_fn.redrawLine = function (drawLine, withTransition) {
return [
(withTransition ? this.mainLine.transition() : this.mainLine)
.attr("d", drawLine)
.style("stroke", $$.color)
.style("opacity", 1));
.style("stroke", this.color)
.style("opacity", 1)
];
};
c3_chart_internal_fn.generateDrawLine = function (lineIndices, isSub) {
var $$ = this, config = $$.config,
@ -199,7 +200,7 @@ c3_chart_internal_fn.lineWithRegions = function (d, x, y, _regions) {
};
c3_chart_internal_fn.redrawArea = function (durationForExit) {
c3_chart_internal_fn.updateArea = function (durationForExit) {
var $$ = this, d3 = $$.d3;
$$.mainArea = $$.main.selectAll('.' + CLASS.areas).selectAll('.' + CLASS.area)
.data($$.lineData.bind($$));
@ -213,12 +214,13 @@ c3_chart_internal_fn.redrawArea = function (durationForExit) {
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForArea = function (transitions, drawArea) {
var $$ = this;
transitions.push($$.mainArea.transition()
c3_chart_internal_fn.redrawArea = function (drawArea, withTransition) {
return [
(withTransition ? this.mainArea.transition() : this.mainArea)
.attr("d", drawArea)
.style("fill", $$.color)
.style("opacity", $$.orgAreaOpacity));
.style("fill", this.color)
.style("opacity", this.orgAreaOpacity)
];
};
c3_chart_internal_fn.generateDrawArea = function (areaIndices, isSub) {
var $$ = this, config = $$.config, area = $$.d3.svg.area(),
@ -226,7 +228,7 @@ c3_chart_internal_fn.generateDrawArea = function (areaIndices, isSub) {
yScaleGetter = isSub ? $$.getSubYScale : $$.getYScale,
xValue = function (d) { return (isSub ? $$.subxx : $$.xx).call($$, d); },
value0 = function (d, i) {
return config.data_groups.length > 0 ? getPoints(d, i)[0][1] : yScaleGetter.call($$, d.id)(0);
return config.data_groups.length > 0 ? getPoints(d, i)[0][1] : yScaleGetter.call($$, d.id)($$.getAreaBaseValue(d.id));
},
value1 = function (d, i) {
return config.data_groups.length > 0 ? getPoints(d, i)[1][1] : yScaleGetter.call($$, d.id)(d.value);
@ -253,7 +255,9 @@ c3_chart_internal_fn.generateDrawArea = function (areaIndices, isSub) {
return path ? path : "M 0 0";
};
};
c3_chart_internal_fn.getAreaBaseValue = function () {
return 0;
};
c3_chart_internal_fn.generateGetAreaPoints = function (areaIndices, isSub) { // partial duplication of generateGetBarPoints
var $$ = this, config = $$.config,
areaTargetsNum = areaIndices.__max__ + 1,
@ -280,7 +284,7 @@ c3_chart_internal_fn.generateGetAreaPoints = function (areaIndices, isSub) { //
};
c3_chart_internal_fn.redrawCircle = function () {
c3_chart_internal_fn.updateCircle = function () {
var $$ = this;
$$.mainCircle = $$.main.selectAll('.' + CLASS.circles).selectAll('.' + CLASS.circle)
.data($$.lineOrScatterData.bind($$));
@ -292,16 +296,18 @@ c3_chart_internal_fn.redrawCircle = function () {
.style("opacity", $$.initialOpacityForCircle.bind($$));
$$.mainCircle.exit().remove();
};
c3_chart_internal_fn.addTransitionForCircle = function (transitions, cx, cy) {
var $$ = this;
transitions.push($$.mainCircle.transition()
.style('opacity', $$.opacityForCircle.bind($$))
.style("fill", $$.color)
c3_chart_internal_fn.redrawCircle = function (cx, cy, withTransition) {
var selectedCircles = this.main.selectAll('.' + CLASS.selectedCircle);
return [
(withTransition ? this.mainCircle.transition() : this.mainCircle)
.style('opacity', this.opacityForCircle.bind(this))
.style("fill", this.color)
.attr("cx", cx)
.attr("cy", cy));
transitions.push($$.main.selectAll('.' + CLASS.selectedCircle).transition()
.attr("cy", cy),
(withTransition ? selectedCircles.transition() : selectedCircles)
.attr("cx", cx)
.attr("cy", cy));
.attr("cy", cy)
];
};
c3_chart_internal_fn.circleX = function (d) {
return d.x || d.x === 0 ? this.x(d.x) : null;

135
src/subchart.js

@ -13,9 +13,7 @@ c3_chart_internal_fn.initSubchart = function () {
var $$ = this, config = $$.config,
context = $$.context = $$.svg.append("g").attr("transform", $$.getTranslate('context'));
if (!config.subchart_show) {
context.style('visibility', 'hidden');
}
context.style('visibility', config.subchart_show ? 'visible' : 'hidden');
// Define g for chart area
context.append('g')
@ -34,9 +32,7 @@ c3_chart_internal_fn.initSubchart = function () {
context.append("g")
.attr("clip-path", $$.clipPath)
.attr("class", CLASS.brush)
.call($$.brush)
.selectAll("rect")
.attr(config.axis_rotated ? "width" : "height", config.axis_rotated ? $$.width2 : $$.height2);
.call($$.brush);
// ATTENTION: This must be called AFTER chart added
// Add Axis
@ -55,6 +51,7 @@ c3_chart_internal_fn.updateTargetsForSubchart = function (targets) {
classAreas = $$.classAreas.bind($$);
if (config.subchart_show) {
//-- Bar --//
contextBarUpdate = context.select('.' + CLASS.chartBars).selectAll('.' + CLASS.chartBar)
.data(targets)
.attr('class', classChartBar);
@ -78,17 +75,74 @@ c3_chart_internal_fn.updateTargetsForSubchart = function (targets) {
// Area
contextLineEnter.append("g")
.attr("class", classAreas);
//-- Brush --//
context.selectAll('.' + CLASS.brush + ' rect')
.attr(config.axis_rotated ? "width" : "height", config.axis_rotated ? $$.width2 : $$.height2);
}
};
c3_chart_internal_fn.updateBarForSubchart = function (durationForExit) {
var $$ = this;
$$.contextBar = $$.context.selectAll('.' + CLASS.bars).selectAll('.' + CLASS.bar)
.data($$.barData.bind($$));
$$.contextBar.enter().append('path')
.attr("class", $$.classBar.bind($$))
.style("stroke", 'none')
.style("fill", $$.color);
$$.contextBar
.style("opacity", $$.initialOpacity.bind($$));
$$.contextBar.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.redrawBarForSubchart = function (drawBarOnSub, withTransition, duration) {
(withTransition ? this.contextBar.transition().duration(duration) : this.contextBar)
.attr('d', drawBarOnSub)
.style('opacity', 1);
};
c3_chart_internal_fn.updateLineForSubchart = function (durationForExit) {
var $$ = this;
$$.contextLine = $$.context.selectAll('.' + CLASS.lines).selectAll('.' + CLASS.line)
.data($$.lineData.bind($$));
$$.contextLine.enter().append('path')
.attr('class', $$.classLine.bind($$))
.style('stroke', $$.color);
$$.contextLine
.style("opacity", $$.initialOpacity.bind($$));
$$.contextLine.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.redrawLineForSubchart = function (drawLineOnSub, withTransition, duration) {
(withTransition ? this.contextLine.transition().duration(duration) : this.contextLine)
.attr("d", drawLineOnSub)
.style('opacity', 1);
};
c3_chart_internal_fn.updateAreaForSubchart = function (durationForExit) {
var $$ = this, d3 = $$.d3;
$$.contextArea = $$.context.selectAll('.' + CLASS.areas).selectAll('.' + CLASS.area)
.data($$.lineData.bind($$));
$$.contextArea.enter().append('path')
.attr("class", $$.classArea.bind($$))
.style("fill", $$.color)
.style("opacity", function () { $$.orgAreaOpacity = +d3.select(this).style('opacity'); return 0; });
$$.contextArea
.style("opacity", 0);
$$.contextArea.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
};
c3_chart_internal_fn.redrawAreaForSubchart = function (drawAreaOnSub, withTransition, duration) {
(withTransition ? this.contextArea.transition().duration(duration) : this.contextArea)
.attr("d", drawAreaOnSub)
.style("fill", this.color)
.style("opacity", this.orgAreaOpacity);
};
c3_chart_internal_fn.redrawSubchart = function (withSubchart, transitions, duration, durationForExit, areaIndices, barIndices, lineIndices) {
var $$ = this, d3 = $$.d3, context = $$.context, config = $$.config,
contextLine, contextArea, contextBar, drawAreaOnSub, drawBarOnSub, drawLineOnSub,
barData = $$.barData.bind($$),
lineData = $$.lineData.bind($$),
classBar = $$.classBar.bind($$),
classLine = $$.classLine.bind($$),
classArea = $$.classArea.bind($$),
initialOpacity = $$.initialOpacity.bind($$);
var $$ = this, d3 = $$.d3, config = $$.config,
drawAreaOnSub, drawBarOnSub, drawLineOnSub;
$$.context.style('visibility', config.subchart_show ? 'visible' : 'hidden');
// subchart
if (config.subchart_show) {
@ -107,51 +161,14 @@ c3_chart_internal_fn.redrawSubchart = function (withSubchart, transitions, durat
drawAreaOnSub = $$.generateDrawArea(areaIndices, true);
drawBarOnSub = $$.generateDrawBar(barIndices, true);
drawLineOnSub = $$.generateDrawLine(lineIndices, true);
// bars
contextBar = context.selectAll('.' + CLASS.bars).selectAll('.' + CLASS.bar)
.data(barData);
contextBar.enter().append('path')
.attr("class", classBar)
.style("stroke", 'none')
.style("fill", $$.color);
contextBar
.style("opacity", initialOpacity)
.transition().duration(duration)
.attr('d', drawBarOnSub)
.style('opacity', 1);
contextBar.exit().transition().duration(duration)
.style('opacity', 0)
.remove();
// lines
contextLine = context.selectAll('.' + CLASS.lines).selectAll('.' + CLASS.line)
.data(lineData);
contextLine.enter().append('path')
.attr('class', classLine)
.style('stroke', $$.color);
contextLine
.style("opacity", initialOpacity)
.transition().duration(duration)
.attr("d", drawLineOnSub)
.style('opacity', 1);
contextLine.exit().transition().duration(duration)
.style('opacity', 0)
.remove();
// area
contextArea = context.selectAll('.' + CLASS.areas).selectAll('.' + CLASS.area)
.data(lineData);
contextArea.enter().append('path')
.attr("class", classArea)
.style("fill", $$.color)
.style("opacity", function () { $$.orgAreaOpacity = +d3.select(this).style('opacity'); return 0; });
contextArea
.style("opacity", 0)
.transition().duration(duration)
.attr("d", drawAreaOnSub)
.style("fill", $$.color)
.style("opacity", $$.orgAreaOpacity);
contextArea.exit().transition().duration(durationForExit)
.style('opacity', 0)
.remove();
$$.updateBarForSubchart(duration);
$$.updateLineForSubchart(duration);
$$.updateAreaForSubchart(duration);
$$.redrawBarForSubchart(drawBarOnSub, duration, duration);
$$.redrawLineForSubchart(drawLineOnSub, duration, duration);
$$.redrawAreaForSubchart(drawAreaOnSub, duration, duration);
}
}
};

16
src/text.js

@ -19,7 +19,7 @@ c3_chart_internal_fn.updateTargetsForText = function (targets) {
mainTextEnter.append('g')
.attr('class', classTexts);
};
c3_chart_internal_fn.redrawText = function (durationForExit) {
c3_chart_internal_fn.updateText = function (durationForExit) {
var $$ = this, config = $$.config,
barOrLineData = $$.barOrLineData.bind($$),
classText = $$.classText.bind($$);
@ -32,20 +32,20 @@ c3_chart_internal_fn.redrawText = function (durationForExit) {
.style("fill", function (d) { return $$.color(d); })
.style("fill-opacity", 0);
$$.mainText
.text(function (d, i, j) { return $$.formatByAxisId($$.getAxisId(d.id))(d.value, d.id, i, j); });
.text(function (d, i, j) { return $$.dataLabelFormat(d.id)(d.value, d.id, i, j); });
$$.mainText.exit()
.transition().duration(durationForExit)
.style('fill-opacity', 0)
.remove();
};
c3_chart_internal_fn.addTransitionForText = function (transitions, xForText, yForText, forFlow) {
var $$ = this,
opacityForText = forFlow ? 0 : $$.opacityForText.bind($$);
transitions.push($$.mainText.transition()
c3_chart_internal_fn.redrawText = function (xForText, yForText, forFlow, withTransition) {
return [
(withTransition ? this.mainText.transition() : this.mainText)
.attr('x', xForText)
.attr('y', yForText)
.style("fill", $$.color)
.style("fill-opacity", opacityForText));
.style("fill", this.color)
.style("fill-opacity", forFlow ? 0 : this.opacityForText.bind(this))
];
};
c3_chart_internal_fn.getTextRect = function (text, cls) {
var body = this.d3.select('body').classed('c3', true),

44
src/tooltip.js

@ -38,8 +38,9 @@ c3_chart_internal_fn.getTooltipContent = function (d, defaultTitleFormat, defaul
text = "<table class='" + CLASS.tooltip + "'>" + (title || title === 0 ? "<tr><th colspan='2'>" + title + "</th></tr>" : "");
}
name = nameFormat(d[i].name, d[i].ratio, d[i].id, d[i].index);
value = valueFormat(d[i].value, d[i].ratio, d[i].id, d[i].index);
if (value !== undefined) {
name = nameFormat(d[i].name, d[i].ratio, d[i].id, d[i].index);
bgcolor = $$.levelColor ? $$.levelColor(d[i].value) : color(d[i].id);
text += "<tr class='" + CLASS.tooltipName + "-" + d[i].id + "'>";
@ -47,24 +48,17 @@ c3_chart_internal_fn.getTooltipContent = function (d, defaultTitleFormat, defaul
text += "<td class='value'>" + value + "</td>";
text += "</tr>";
}
}
return text + "</table>";
};
c3_chart_internal_fn.showTooltip = function (selectedData, mouse) {
var $$ = this, config = $$.config;
var tWidth, tHeight, svgLeft, tooltipLeft, tooltipRight, tooltipTop, chartRight;
c3_chart_internal_fn.tooltipPosition = function (dataToShow, tWidth, tHeight, element) {
var $$ = this, config = $$.config, d3 = $$.d3;
var svgLeft, tooltipLeft, tooltipRight, tooltipTop, chartRight;
var forArc = $$.hasArcType(),
dataToShow = selectedData.filter(function (d) { return d && isValue(d.value); });
if (dataToShow.length === 0 || !config.tooltip_show) {
return;
}
$$.tooltip.html(config.tooltip_contents.call($$, selectedData, $$.getXAxisTickFormat(), $$.getYFormat(forArc), $$.color)).style("display", "block");
// Get tooltip dimensions
tWidth = $$.tooltip.property('offsetWidth');
tHeight = $$.tooltip.property('offsetHeight');
mouse = d3.mouse(element);
// Determin tooltip position
if (forArc) {
tooltipLeft = ($$.width / 2) + mouse[0];
tooltipLeft = (($$.width - ($$.isLegendRight ? $$.getLegendWidth() : 0)) / 2) + mouse[0];
tooltipTop = ($$.height / 2) + mouse[1] + 20;
} else {
svgLeft = $$.getSvgLeft(true);
@ -90,10 +84,28 @@ c3_chart_internal_fn.showTooltip = function (selectedData, mouse) {
if (tooltipTop < 0) {
tooltipTop = 0;
}
return {top: tooltipTop, left: tooltipLeft};
};
c3_chart_internal_fn.showTooltip = function (selectedData, element) {
var $$ = this, config = $$.config;
var tWidth, tHeight, position;
var forArc = $$.hasArcType(),
dataToShow = selectedData.filter(function (d) { return d && isValue(d.value); }),
positionFunction = config.tooltip_position || c3_chart_internal_fn.tooltipPosition;
if (dataToShow.length === 0 || !config.tooltip_show) {
return;
}
$$.tooltip.html(config.tooltip_contents.call($$, selectedData, $$.getXAxisTickFormat(), $$.getYFormat(forArc), $$.color)).style("display", "block");
// Get tooltip dimensions
tWidth = $$.tooltip.property('offsetWidth');
tHeight = $$.tooltip.property('offsetHeight');
position = positionFunction.call(this, dataToShow, tWidth, tHeight, element);
// Set tooltip
$$.tooltip
.style("top", tooltipTop + "px")
.style("left", tooltipLeft + 'px');
.style("top", position.top + "px")
.style("left", position.left + 'px');
};
c3_chart_internal_fn.hideTooltip = function () {
this.tooltip.style("display", "none");

Loading…
Cancel
Save