How can I add like a textbox with longer text to a chart in vega-lite? - vega-lite

I have an Scatterplot with a second layer for two lines with benchmark-data, now I need like a legend for these lines. I already managed to include them to the legend of the Scatterplot, but that does not help, as the legends name does not fit for these additional lines and especially the despriction is too long, to be displayed as a legend entry.
What I have is this (the lowest two points in the legend):
Only two words for description in legend
And what I need is this:
colored textboxes with description
const spec = {
...sharedChartSpec,
height: 350,
config: {
axis: {
tickColor: 'lightgrey',
titleFontSize: 15,
grid:false
},
style: {
cell: {
stroke: "transparent"
}
},
},
// title: {text: "Spezifischer Energieverbrauch [kWh/m2]", align: "center"},
layer: [
{
data: {name: 'values'}, // note: vega-lite data attribute is a plain object instead of an array,
mark: {type: 'circle', size: 20, opacity: 1},
encoding: {
x: {field: 'constructionYear', type: 'temporal', timeUnit: 'year', axis: {title: ''}, "scale": {"domain": [1880,2022]}},
y: {field: 'consumption_perm2', type: 'quantitative', axis: {title: null}, "scale": {"domain": [0, 350]}},
color: {field: 'heater', type: 'nominal', scale: customScale, title: 'Energieträger'},
opacity: {condition: {param: "Heater", value: 1},
value: 0.2},
tooltip: [
{field: "address", type: "nominal", title:'Adresse', fontSize:5},
{field: "town", type: "nominal", title:'Ort'},
{field: "heater", type: "nominal", title:'Primärer Energieträger'},
{field: "consumption_perm2", type: "quantitative", title:'Verbrauch in kWh/m2'},
{field: "EEK", type: "nominal", title:'EEK'}
]
},
params: [
{
"name": "grid",
"select": "interval",
"bind": "scales"
},
{
"name": "Heater",
"select": {"type": "point", "fields": ["heater"]},
"bind": "legend"
}
],
},
{
data: {name: 'benchmark'},
mark: {type: 'line'},
encoding: {
x: {field: 'constructionYear', type: 'temporal', timeUnit: 'year', axis: {title: null}},
y: {field: 'consumption_perm2', type: 'quantitative', axis: {title: null}},
color: {field: 'typ', type: 'nominal', scale: customScale},
}
},
{
data: {name: 'demand'},
mark: {type: 'line'},
encoding: {
x: {field: 'constructionYear', type: 'temporal', timeUnit: 'year', axis: {title: null}},
y: {field: 'consumption_perm2', type: 'quantitative', axis: {title: null}},
color: {field: 'typ', type: 'nominal', scale: customScale},
},
}
]
}

You can place your text wherever you want using dx and dy properties.
{
"$schema": "https://vega.github.io/schema/vega-lite/v5.json",
"description": "Google's stock price over time.",
"data": {"url": "data/stocks.csv"},
"transform": [{"filter": "datum.symbol==='GOOG'"}],
"layer": [
{
"mark": "line",
"encoding": {
"x": {"field": "date", "type": "temporal"},
"y": {"field": "price", "type": "quantitative"}
}
},
{
"data": {"values": [{}]},
"mark": {
"type": "text",
"align": "left",
"baseline": "bottom",
"text": ["Line 1", "Line 2"],
"dx": 150,
"dy": -50
}
}
]
}

I can't reuse your code but here is an example of multiline annotation which you should be able to build on.
Editor
{
"$schema": "https://vega.github.io/schema/vega-lite/v5.json",
"description": "Google's stock price over time.",
"data": {"url": "data/stocks.csv"},
"transform": [{"filter": "datum.symbol==='GOOG'"}],
"layer": [
{
"mark": "line",
"encoding": {
"x": {"field": "date", "type": "temporal"},
"y": {"field": "price", "type": "quantitative"}
}
},
{
"encoding": {
"x": {"aggregate": "max", "field": "date", "type": "temporal"},
"y": {
"aggregate": {"argmax": "date"},
"field": "price",
"type": "quantitative"
}
},
"mark": {
"type": "text",
"align": "left",
"baseline": "bottom",
"text": ["Line 1", "Line 2"]
}
}
]
}

Related

Axis label dissappear when adding zooming (Vega-Lite)

I try to show timeseries data as point charts with two x-axis labels (2 text marks as my main x-axis attribute should not be displayed), mainly one at the top and one at the bottom. This works with a layered approach but as soon as I add the zoomable parameter to the visual, the text mark for the axes labels disappear. Is there a way on how to solve this issue?
That's how the visual looks like - without adding the zooming feature:
Timeseries point visual with two measure attributes and top and bottom x-axis label
What I’ve tried so far
I tried to position the params at different positions in the code as I am also using a vertical rule but it did not work out.
I also tried to make use of the scale resolve but I was neither successful.
Within the resolve, I tried to make use of the labelBound axis information and set it to false.
Basically, here is the code that I am currently using
{
"data": {
"name": "dataset"
},
"encoding": {
"x": {
"field": "TIMESTAMP",
"timeUnit": "utcyearmonthdatehoursminutes",
"type": "ordinal",
"axis": {
"grid": false,
"title": null,
"orient": "bottom",
"labels": false
}
}
},
"vconcat": [
{
"hconcat": [
{
"layer": [
{
"transform": [
{
"fold": [
"ATTRIBUTE1",
"ATTRIBUTE2"
],
"as": [
"measure1",
"temp1"
]
}
],
"mark": {
"type": "point",
"filled": true,
"size": 20
},
"height": 150,
"width": 700,
"encoding": {
"x": {
"timeUnit": "utcyearmonthdatehoursminutes",
"field": "TIMESTAMP",
"type": "ordinal",
"axis": {
"title": null,
"labels": false,
"ticks": false
}
},
"y": {
"field": "temp1",
"type": "quantitative",
"axis": {
"title": null
},
"scale": {
"zero": false,
"domain": [
450,
490
]
}
},
"color": {
"field": "measure1",
"type": "nominal",
"legend": {
"title": "Measures",
"orient": "right"
}
},
"opacity": {
"condition": [
{
"param": "legendhighlight",
"value": 1,
"empty": false
},
{
"param": "hover",
"value": 1,
"empty": false
}
],
"value": 0.1
}
}
},
{
"mark": {
"type": "text",
"align": "left",
"angle": -90,
"fontSize": 10
},
"encoding": {
"x": {
"timeUnit": "utcyearmonthdatehoursminutes",
"field": "TIMESTAMP",
"type": "ordinal",
"axis": {
"title": null,
"labels": false
}
},
"text": {
"field": "Attribute_TopX"
},
"y": {
"value": -5
},
"color": {
"condition": [
{
"test": "datum['COLORATTRIBUTE']=='COLOR_ITEM1'",
"value": "green"
},
{
"test": "datum['COLORATTRIBUTE']=='COLOR_ITEM2'",
"value": "steelblue"
}
],
"value": "black"
}
}
},{
"mark": {
"type": "text",
"align": "right",
"angle": -90,
"fontSize": 10
},
"encoding": {
"x": {
"timeUnit": "utcyearmonthdatehoursminutes",
"field": "TIMESTAMP",
"type": "ordinal",
"axis": {
"title": null,
"labels": false
}
},
"text": {
"field": "Attribute_BottomX"
},
"y": {
"value": "height"
},
"color": {
"condition": [
{
"test": "datum['COLORATTRIBUTE']=='COLOR_ITEM1'",
"value": "green"
},
{
"test": "datum['COLORATTRIBUTE']=='COLOR_ITEM2'",
"value": "steelblue"
}
],
"value": "black"
}
}
},
{
"mark": "rule",
"encoding": {
"x": {
"field": "TIMESTAMP",
"type": "temporal"
},
"opacity": {
"condition": [
{
"param": "hover",
"value": 0.8,
"empty": false
}
],
"value": 0
},
"size": {
"value": 1
},
"params": [
{
"name": "hover",
"select": {
"type": "point",
"encodings": [
"x"
],
"nearest": true,
"on": "mouseover"
}
},
{
"name": "legendhighlight",
"select": {
"type": "point",
"fields": [
"measure1"
]
},
"bind": "legend"
}
]
}
]
},
{
"layer": [
{
"transform": [
{
"fold": [
"ATTRIBUTE1",
"ATTRIBUTE2"
],
"as": [
"measure1",
"temp1"
]
}
],
"mark": {
"type": "boxplot"
},
"height": 150,
"width": 100,
"encoding": {
"x": {
"field": "measure1",
"type": "nominal",
"axis": {
"labels": false,
"ticks": false,
"title": null
}
},
"y": {
"field": "temp1",
"type": "quantitative",
"axis": {
"labels": false,
"ticks": false,
"title": null
},
"scale": {
"zero": false
}
},
"color": {
"field": "measure1",
"type": "nominal",
"legend": null
}
}
}
]
}
]
}
],
"resolve": {
"scale": {
"y": "independent",
"x": "shared",
"color": "independent"
}
}
}
And here is the params code that I try to add using Vega-Lite v5:
"params": [
{
"name": "grid",
"select": "interval",
"bind": "scales"
}
],
Thank you for your help!

Wrap title and sub title to next lines in pie amchart 3

I am using pie amchart v3, and i am using allLabels property to display the title and subtitle. But the problem is that, title is not wrapping to the next line as shown below
How to Wrap the text "TOP BUS TYPES: BUS TYPES" to next line?
Below is my code.
const chart = this.AmCharts.makeChart( "mychart", {
"type": "pie",
"theme": "light",
"dataProvider": busvalue,
"titleField": "title",
"valueField": "value",
"labelsEnabled": false,
"radius": "40%",
"innerRadius": "60%",
"colorField": "color",
"allLabels": [{
"y": "48%",
"align": "center",
"size": 17,
"bold": true,
"text": 'TOP BUS TYPES: BUS TYPES',
"color":'#000000'
},{
"y": "52%",
"align": "center",
"size": 12,
"text": ''
"color": '#000000
}],
...
});
}
There isn't any mechanism to automatically wrap free labels (allLabels) in amcharts v3. You have to insert your own newline characters as needed in your string, e.g. "text": 'TOP BUS TYPES:\nBUS TYPES'
AmCharts.makeChart("mychart", {
"type": "pie",
"theme": "light",
"dataProvider": [{
"title": "1",
"value": 10
}, {
"title": "2",
"value": 10
}, {
"title": "3",
"value": 10
}],
"titleField": "title",
"valueField": "value",
"labelsEnabled": false,
"radius": "40%",
"innerRadius": "60%",
"colorField": "color",
"allLabels": [{
"y": "48%",
"align": "center",
"size": 17,
"bold": true,
"text": 'TOP BUS TYPES:\nBUS TYPES',
"color": '#000000'
}, {
"y": "52%",
"align": "center",
"size": 12,
"text": '',
"color": '#000000'
}]
});
<script src="https://www.amcharts.com/lib/3/amcharts.js"></script>
<script src="https://www.amcharts.com/lib/3/pie.js"></script>
<script src="https://www.amcharts.com/lib/3/themes/light.js"></script>
<div id="mychart" style="width: 100%; height: 400px;"></div>

Rotate x-axis label in vega heatmap?

I have built a heat map of correlation matrix
How can I rotate the x-axis label
Is it possible to make the legend vertical like
I tried
"axes": [
{
"orient": "bottom",
"scale": "x",
"labelAngle": -45,
"tickOffset": 0,
"labelAlign": "right",
"domain": false,
"title": "Features"
},
{
"orient": "left",
"scale": "y",
"domain": false,
"title": "Features"
}
],
"legends": [
{
"orient": "right",
"direction" : "vertical",
"fill": "color",
"type": "gradient",
"title": "Correlation",
"titleFontSize": 12,
"titlePadding": 4,
"gradientLength": {"signal": "height - 16"}
}
],
but not happening
i am using vega "https://vega.github.io/schema/vega/v3.json" schema
Rotating the x-axis names, this worked
{
"orient": "bottom",
"scale": "x",
"labelOverlap":false,
"domain": false,
"title": "Features",
"encode": {
"labels": {
"update": {
"angle": {"value": -50},
"fontSize": {"value": 10},
"align": {"value": "right"}
}
}
}
},

How to avoid zoom conflict in a line chart with layer?

VEGA-lite is not perfect, but is very good, and in general for something that looks like a bug, there are a workaround... So I supposing that in this "bug" we have a workaround.
((edit after answer: it is not a real bug, is a "semantic bug" on the specification language))
The strange behaviour, a "semantic bug": I was using selection: { "grid": {"type":"interval", "bind":"scales"} } for zoom, in a trivial context, with simple mark: 'line'. When I add layer, it stopts to work.
{
title: "Número de registros por minuto (n_count normalizado)",
$schema: vglVers,
data: { "url":"mySQLtable" },
selection: { "grid": {"type":"interval", "bind":"scales"} }, // was working with simple mark
//mark: 'line',
width:340,
encoding: {
x: {"field": "instant", "type": "temporal"},
y: {"field": "n_pmin", "type": "quantitative"},
color: {"field": "symbol", "type": "nominal"}
},
layer: [
{
"mark": {"type": "line", "point": true},
"transform": [{"filter": "datum.symbol == 'n_pmin'"}]
},
{ "mark": {"type": "line"}, "transform": [{"filter": "datum.symbol != 'n_pmin'"}] }
]
}
The workaround: as #jakevdp commented here,
"the interval selection must be added to one of the layers". But
How to do this "interval selection"?
The data on my chart is not static, I need a interval that changes with it, so, not make sense to set a interval.
The "interval selection" I referred to is the interval selection definition within your chart:
selection: { "grid": {"type":"interval", "bind":"scales"} }
You cannot declare it in the top-level chart; you must declare it in one of the layers:
{
title: "Número de registros por minuto (n_count normalizado)",
$schema: vglVers,
data: { "url":"mySQLtable" },
width:340,
encoding: {
x: {"field": "instant", "type": "temporal"},
y: {"field": "n_pmin", "type": "quantitative"},
color: {"field": "symbol", "type": "nominal"}
},
layer: [
{
"mark": {"type": "line", "point": true},
"transform": [{"filter": "datum.symbol == 'n_pmin'"}],
"selection": {"grid": {"type":"interval", "bind":"scales"}},
},
{
"mark": {"type": "line"},
"transform": [{"filter": "datum.symbol != 'n_pmin'"}]
}
]
}
Your issue is not a bug, nor is my solution a workaround: the vega-lite schema specifies that selections must be declared within a unit spec (i.e. an individual layer).

Is there a way to add a line on top of a histogram?

My best attempt at it so far : Direct link to Vega-editor
I created 2 layers with the same data, remove padding for the 'bar' layer and add a step interpolation for the 'line' layer but I can't find a way to make the line starts at the vertical axis and ends at the right of chart.
The spec (sorry I removed lines because StackOverflow doesn't want to let me post it if the ratio text/code is not enough) :
{
"$schema": "https://vega.github.io/schema/vega-lite/v4.json",
"datasets": ...,
"width": 1130,
"height": 438,
"layer": [
{
"mark": {
"type": "bar",
"opacity": 0.7
},
"encoding": {
"x": {
"scale": {
"padding": 0
},
"field": "Continent",
"type": "nominal"
},
"y": {
"field": "Population",
"type": "quantitative"
}
},
"data": {
"name": "bar"
}
},
{
"mark": {
"type": "line",
"interpolate": "step",
"strokeWidth": 3
},
"encoding": {
"x": {
"axis": {},
"field": "Continent",
"type": "nominal"
},
"y": {
"axis": {},
"field": "Population",
"type": "quantitative"
}
},
"data": {
"name": "line"
}
}
]
}