mirror of
https://github.com/elastic/kibana.git
synced 2025-04-23 17:28:26 -04:00
adding cell labels
This commit is contained in:
parent
56569c4db6
commit
98dbfac2b6
3 changed files with 132 additions and 41 deletions
|
@ -31,7 +31,7 @@
|
|||
<select
|
||||
id="axisScale"
|
||||
class="kuiSelect kuiSideBarSelect"
|
||||
ng-model="vis.params.scale"
|
||||
ng-model="vis.params.valueAxes[0].scale.type"
|
||||
ng-options="mode for mode in vis.type.params.scales"
|
||||
></select>
|
||||
</div>
|
||||
|
@ -42,7 +42,7 @@
|
|||
Scale to Data Bounds
|
||||
</label>
|
||||
<div class="kuiSideBarFormRow__control">
|
||||
<input class="kuiCheckBox" id="defaultYExtents" type="checkbox" ng-model="vis.params.defaultYExtents">
|
||||
<input class="kuiCheckBox" id="defaultYExtents" type="checkbox" ng-model="vis.params.valueAxes[0].scale.defaultYExtents">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
@ -55,15 +55,6 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div class="kuiSideBarFormRow">
|
||||
<label class="kuiSideBarFormRow__label" for="cellLabels">
|
||||
Show Cell Labels
|
||||
</label>
|
||||
<div class="kuiSideBarFormRow__control">
|
||||
<input class="kuiCheckBox" id="cellLabels" type="checkbox" ng-model="vis.params.cellLabels">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="kuiSideBarFormRow">
|
||||
<label class="kuiSideBarFormRow__label" for="colorsNumber">
|
||||
Number of colors
|
||||
|
@ -73,7 +64,7 @@
|
|||
id="colorsNumber"
|
||||
type="range"
|
||||
step="1"
|
||||
min="3"
|
||||
min="2"
|
||||
max="10"
|
||||
class="kuiInput kuiSideBarInput"
|
||||
ng-model="vis.params.colorsNumber"
|
||||
|
@ -81,16 +72,7 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div class="kuiSideBarFormRow">
|
||||
<label class="kuiSideBarFormRow__label" for="setColorRange">
|
||||
Custom Range
|
||||
</label>
|
||||
<div class="kuiSideBarFormRow__control">
|
||||
<input class="kuiCheckBox" id="setColorRange" type="checkbox" ng-model="vis.params.setColorRange">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div ng-if="vis.params.setColorRange">
|
||||
<div>
|
||||
<div class="kuiSideBarCollapsibleTitle">
|
||||
<div
|
||||
class="kuiSideBarCollapsibleTitle__label"
|
||||
|
@ -105,9 +87,14 @@
|
|||
Custom Ranges
|
||||
</span>
|
||||
</div>
|
||||
<input aria-label="enable"
|
||||
ng-model="vis.params.setColorRange"
|
||||
type="checkbox"
|
||||
class="kuiSideBarSectionTitle__action"
|
||||
>
|
||||
</div>
|
||||
|
||||
<div ng-show="isColorRangeOpen" class="kuiSideBarCollapsibleSection">
|
||||
<div ng-if="vis.params.setColorRange" ng-show="isColorRangeOpen" class="kuiSideBarCollapsibleSection">
|
||||
<div class="kuiSideBarSection">
|
||||
<div class="kuiSideBarFormRow" ng-repeat="color in vis.params.colorsRange track by $index">
|
||||
<label class="kuiSideBarFormRow__label" for="{{ 'colorRange' + $index }}">
|
||||
|
@ -129,4 +116,45 @@
|
|||
<div class="text text-center text-info">note: colors can be changed in the legend</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<div class="kuiSideBarCollapsibleTitle">
|
||||
<div
|
||||
class="kuiSideBarCollapsibleTitle__label"
|
||||
ng-click="isLabelsOpen = !isLabelsOpen"
|
||||
>
|
||||
<span
|
||||
aria-hidden="true"
|
||||
ng-class="{ 'fa-caret-down': isLabelsOpen, 'fa-caret-right': !isLabelsOpen }"
|
||||
class="fa fa-caret-right kuiSideBarCollapsibleTitle__caret"
|
||||
></span>
|
||||
<span class="kuiSideBarCollapsibleTitle__text">
|
||||
Show Labels
|
||||
</span>
|
||||
</div>
|
||||
<input aria-label="enable"
|
||||
ng-model="vis.params.valueAxes[0].labels.show"
|
||||
type="checkbox"
|
||||
class="kuiSideBarSectionTitle__action"
|
||||
>
|
||||
</div>
|
||||
<div ng-if="vis.params.valueAxes[0].labels.show" ng-show="isLabelsOpen" class="kuiSideBarCollapsibleSection">
|
||||
<div class="kuiSideBarSection">
|
||||
<div class="kuiSideBarFormRow">
|
||||
<label class="kuiSideBarFormRow__label" for="rotateLabels">
|
||||
Rotate
|
||||
</label>
|
||||
<div class="kuiSideBarFormRow__control">
|
||||
<input
|
||||
id="rotateLabels"
|
||||
class="kuiInput kuiSideBarInput"
|
||||
type="number"
|
||||
ng-model="vis.params.valueAxes[0].labels.rotate"
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
|
|
@ -18,11 +18,7 @@ export default function HeatmapVisType(Private) {
|
|||
addLegend: true,
|
||||
enableHover: false,
|
||||
legendPosition: 'right',
|
||||
scale: 'linear',
|
||||
times: [],
|
||||
addTimeMarker: false,
|
||||
defaultYExtents: false,
|
||||
setYExtents: false,
|
||||
colorsNumber: 4,
|
||||
colorSchema: 'Greens',
|
||||
setColorRange: false,
|
||||
|
@ -30,6 +26,18 @@ export default function HeatmapVisType(Private) {
|
|||
invertColors: false,
|
||||
percentageMode: true,
|
||||
cellLabels: false,
|
||||
valueAxes: [{
|
||||
id: 'ValueAxis-1',
|
||||
type: 'value',
|
||||
scale: {
|
||||
type: 'linear',
|
||||
defaultYExtents: false,
|
||||
},
|
||||
labels: {
|
||||
show: false,
|
||||
rotate: 0,
|
||||
}
|
||||
}]
|
||||
},
|
||||
legendPositions: [{
|
||||
value: 'left',
|
||||
|
|
|
@ -1,4 +1,6 @@
|
|||
import _ from 'lodash';
|
||||
import d3 from 'd3';
|
||||
import $ from 'jquery';
|
||||
import moment from 'moment';
|
||||
import VislibVisualizationsPointSeriesProvider from './_point_series';
|
||||
import heatmapColorFunc from 'ui/vislib/components/color/heatmap_color';
|
||||
|
@ -101,12 +103,15 @@ export default function HeatmapChartFactory(Private) {
|
|||
const colorsRange = this.handler.visConfig.get('colorsRange');
|
||||
const color = this.handler.data.getColorFunc();
|
||||
const labels = this.handler.visConfig.get('legend.labels');
|
||||
const zAxisConfig = this.getValueAxis().axisConfig;
|
||||
const zAxisFormatter = zAxisConfig.get('labels.axisFormatter');
|
||||
const showLabels = zAxisConfig.get('labels.show');
|
||||
|
||||
const layer = svg.append('g')
|
||||
.attr('class', 'series');
|
||||
|
||||
const squares = layer
|
||||
.selectAll('rect')
|
||||
.selectAll('g.square')
|
||||
.data(data.values);
|
||||
|
||||
squares
|
||||
|
@ -121,7 +126,6 @@ export default function HeatmapChartFactory(Private) {
|
|||
|
||||
barWidth = xScale(end) - xScale(start);
|
||||
if (!isHorizontal) barWidth *= -1;
|
||||
barWidth = barWidth - Math.min(barWidth * 0.25, 15);
|
||||
}
|
||||
|
||||
function x(d) {
|
||||
|
@ -159,24 +163,75 @@ export default function HeatmapChartFactory(Private) {
|
|||
return color(label(d));
|
||||
}
|
||||
|
||||
function widthFunc() {
|
||||
return barWidth || xScale.rangeBand();
|
||||
}
|
||||
function truncateLabel(text, size) {
|
||||
const node = d3.select(text).node();
|
||||
let str = $(node).text();
|
||||
const width = node.getBBox().width;
|
||||
const chars = str.length;
|
||||
const pxPerChar = width / chars;
|
||||
let endChar = 0;
|
||||
const ellipsesPad = 4;
|
||||
|
||||
function heightFunc() {
|
||||
return yScale.rangeBand();
|
||||
}
|
||||
|
||||
if (width > size) {
|
||||
endChar = Math.floor((size / pxPerChar) - ellipsesPad);
|
||||
while (str[endChar - 1] === ' ' || str[endChar - 1] === '-' || str[endChar - 1] === ',') {
|
||||
endChar = endChar - 1;
|
||||
}
|
||||
str = str.substr(0, endChar) + '...';
|
||||
}
|
||||
return str;
|
||||
};
|
||||
|
||||
const squareWidth = barWidth || xScale.rangeBand();
|
||||
const squareHeight = yScale.rangeBand();
|
||||
|
||||
squares
|
||||
.enter()
|
||||
.append('rect')
|
||||
.attr('x', isHorizontal ? x : y)
|
||||
.attr('width', isHorizontal ? widthFunc : heightFunc)
|
||||
.attr('y', isHorizontal ? y : x)
|
||||
.attr('height', isHorizontal ? heightFunc : widthFunc)
|
||||
.append('g')
|
||||
.attr('class', 'square');
|
||||
|
||||
squares.append('rect')
|
||||
.attr('x', x)
|
||||
.attr('width', squareWidth)
|
||||
.attr('y', y)
|
||||
.attr('height', squareHeight)
|
||||
.attr('data-label', label)
|
||||
.attr('fill', z)
|
||||
.attr('style', 'cursor: pointer');
|
||||
.attr('style', 'cursor: pointer; stroke: black; stroke-width: 0.3px');
|
||||
|
||||
// todo: verify that longest label is not longer than the barwidth
|
||||
// or barwidth is not smaller than textheight (and vice versa)
|
||||
//
|
||||
if (showLabels) {
|
||||
const rotate = zAxisConfig.get('labels.rotate');
|
||||
const rotateRad = rotate * Math.PI / 180;
|
||||
const truncate = Math.min(
|
||||
Math.abs(squareWidth / Math.cos(rotateRad)),
|
||||
Math.abs(squareHeight / Math.sin(rotateRad))
|
||||
) - 10;
|
||||
|
||||
squares.append('text')
|
||||
.text(d => zAxisFormatter(d.y))
|
||||
.text(function () {
|
||||
return truncateLabel(this, truncate);
|
||||
})
|
||||
.style('dominant-baseline', 'central')
|
||||
.style('text-anchor', 'middle')
|
||||
.attr('x', function (d) {
|
||||
const center = x(d) + squareWidth / 2;
|
||||
return center;
|
||||
})
|
||||
.attr('y', function (d) {
|
||||
const center = y(d) + squareHeight / 2;
|
||||
return center;
|
||||
})
|
||||
.attr('transform', function (d) {
|
||||
const horizontalCenter = x(d) + squareWidth / 2;
|
||||
const verticalCenter = y(d) + squareHeight / 2;
|
||||
return `rotate(${rotate},${horizontalCenter},${verticalCenter})`;
|
||||
});
|
||||
}
|
||||
|
||||
if (isTooltip) {
|
||||
squares.call(tooltip.render());
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue