étiquetage de l'axe d3

94

Comment ajouter des étiquettes de texte aux axes dans d3?

Par exemple, j'ai un graphique linéaire simple avec un axe x et y.

Sur mon axe des x, j'ai des graduations de 1 à 10. Je veux que le mot «jours» apparaisse en dessous afin que les gens sachent que l'axe des x compte les jours.

De même, sur l'axe des y, j'ai les nombres 1 à 10 sous forme de graduations, et je veux que les mots «sandwiches mangés» apparaissent sur le côté.

Existe-t-il un moyen simple de le faire?

user1474218
la source

Réponses:

164

Les étiquettes d'axe ne sont pas intégrées au composant d'axe de D3 , mais vous pouvez ajouter des étiquettes vous-même simplement en ajoutant un textélément SVG . Un bon exemple de ceci est ma reconstitution du graphique à bulles animé de Gapminder, The Wealth & Health of Nations . L'étiquette de l'axe des x ressemble à ceci:

svg.append("text")
    .attr("class", "x label")
    .attr("text-anchor", "end")
    .attr("x", width)
    .attr("y", height - 6)
    .text("income per capita, inflation-adjusted (dollars)");

Et l'étiquette de l'axe y comme ceci:

svg.append("text")
    .attr("class", "y label")
    .attr("text-anchor", "end")
    .attr("y", 6)
    .attr("dy", ".75em")
    .attr("transform", "rotate(-90)")
    .text("life expectancy (years)");

Vous pouvez également utiliser une feuille de style pour styliser ces étiquettes comme vous le souhaitez, ensemble ( .label) ou individuellement ( .x.label, .y.label).

mbostock
la source
9
J'ai trouvé que cela .attr("transform", "rotate(-90)")fait tourner tout le système de coordination. Ainsi, si vous vous positionnez avec "x" et "y", vous devez échanger les positions par rapport à ce que j'attendais.
lubar
une considération particulière pour le cas de plusieurs graphiques et des étiquettes d'axe voulues sur chacun d'eux?
ted.strauss
31

Dans la nouvelle version de D3js (à partir de la version 3), lorsque vous créez un axe de graphique via une d3.svg.axis()fonction, vous avez accès à deux méthodes appelées tickValueset tickFormatqui sont intégrées à l'intérieur de la fonction afin que vous puissiez spécifier les valeurs pour lesquelles vous avez besoin des graduations et dans quoi format dans lequel vous voulez que le texte apparaisse:

var formatAxis = d3.format("  0");
var axis = d3.svg.axis()
        .scale(xScale)
        .tickFormat(formatAxis)
        .ticks(3)
        .tickValues([100, 200, 300]) //specify an array here for values
        .orient("bottom");
ambodi
la source
Belle explication, mais il semble que l'OP ait déjà des graduations sur leurs axes.
Michael Scheper
1
OP? Je ne comprends pas l'abréviation, désolé.
ambodi
Pas de soucis. OP = 'Original Post' ou 'Original Poster'. (Les moteurs de recherche et urbandictionary.com sont de très bonnes références pour des abréviations comme celle-ci.)
Michael Scheper
13

Si vous voulez l'étiquette de l'axe y au milieu de l'axe y comme je l'ai fait:

  1. Faire pivoter le texte de 90 degrés avec l'ancre de texte au milieu
  2. Traduire le texte par son milieu
    • position x: pour éviter le chevauchement des étiquettes de graduation de l'axe y ( -50)
    • position y: pour correspondre au milieu de l'axe y ( chartHeight / 2)

Exemple de code:

var axisLabelX = -50;
var axisLabelY = chartHeight / 2;

chartArea
    .append('g')
    .attr('transform', 'translate(' + axisLabelX + ', ' + axisLabelY + ')')
    .append('text')
    .attr('text-anchor', 'middle')
    .attr('transform', 'rotate(-90)')
    .text('Y Axis Label')
    ;

Cela empêche la rotation de l'ensemble du système de coordonnées comme mentionné par lubar ci-dessus.

Michael Clark
la source
Bien sûr, j'ai ajouté plus de détails, est-ce mieux?
Michael Clark
1
Oui! Je l'ai déjà voté, parce que votre réponse initiale m'a mis sur la bonne voie, mais dans l'état actuel des choses, les futurs lecteurs n'auront pas à le manipuler autant pour comprendre ce que tout cela signifie. :-) À votre santé.
Michael Scheper
2

Si vous travaillez dans d3.v4, comme suggéré, vous pouvez utiliser cette instance offrant tout ce dont vous avez besoin.

Vous voudrez peut-être simplement remplacer les données de l'axe X par vos «jours», mais n'oubliez pas d'analyser correctement les valeurs de chaîne et de ne pas appliquer la concaténation.

parseTime pourrait tout aussi bien faire l'affaire pour les jours avec un format de date?

d3.json("data.json", function(error, data) {
if (error) throw error;

data.forEach(function(d) {
  d.year = parseTime(d.year);
  d.value = +d.value;
});

x.domain(d3.extent(data, function(d) { return d.year; }));
y.domain([d3.min(data, function(d) { return d.value; }) / 1.005, d3.max(data, function(d) { return d.value; }) * 1.005]);

g.append("g")
    .attr("class", "axis axis--x")
    .attr("transform", "translate(0," + height + ")")
    .call(d3.axisBottom(x));


g.append("g")
    .attr("class", "axis axis--y")
    .call(d3.axisLeft(y).ticks(6).tickFormat(function(d) { return parseInt(d / 1000) + "k"; }))
  .append("text")
    .attr("class", "axis-title")
    .attr("transform", "rotate(-90)")
    .attr("y", 6)
    .attr("dy", ".71em")
    .style("text-anchor", "end")
    .attr("fill", "#5D6971")
    .text("Population)");

violon avec css / js global

因特网 的 小熊
la source
1

D3 fournit un ensemble de composants de bas niveau que vous pouvez utiliser pour assembler des graphiques. Vous recevez les blocs de construction, un composant d'axe, la jointure de données, la sélection et le SVG. C'est votre travail de les assembler pour former un graphique!

Si vous voulez un graphique conventionnel, c'est-à-dire une paire d'axes, des étiquettes d'axes, un titre de graphique et une zone de traçage, pourquoi ne pas jeter un œil à d3fc ? il s'agit d'un ensemble open source de composants D3 de plus haut niveau. Il comprend un composant de graphique cartésien qui pourrait être ce dont vous avez besoin:

var chart = fc.chartSvgCartesian(
    d3.scaleLinear(),
    d3.scaleLinear()
  )
  .xLabel('Value')
  .yLabel('Sine / Cosine')
  .chartLabel('Sine and Cosine')
  .yDomain(yExtent(data))
  .xDomain(xExtent(data))
  .plotArea(multi);

// render
d3.select('#sine')
  .datum(data)
  .call(chart);

Vous pouvez voir un exemple plus complet ici: https://d3fc.io/examples/simple/index.html

Coline
la source
0
chart.xAxis.axisLabel('Label here');

ou

xAxis: {
   axisLabel: 'Label here'
},
Ravi Tej
la source