@@ -1281,20 +1281,18 @@ function alignHoverText(hoverLabels, rotateLabels) {
12811281 // box around it
12821282 hoverLabels . each ( function ( d ) {
12831283 var g = d3 . select ( this ) ;
1284- if ( d . del ) {
1285- g . remove ( ) ;
1286- return ;
1287- }
1284+ if ( d . del ) return g . remove ( ) ;
12881285
1289- var horzSign = d . anchor === 'end' ? - 1 : 1 ;
12901286 var tx = g . select ( 'text.nums' ) ;
1291- var alignShift = { start : 1 , end : - 1 , middle : 0 } [ d . anchor ] ;
1287+ var anchor = d . anchor ;
1288+ var horzSign = anchor === 'end' ? - 1 : 1 ;
1289+ var alignShift = { start : 1 , end : - 1 , middle : 0 } [ anchor ] ;
12921290 var txx = alignShift * ( HOVERARROWSIZE + HOVERTEXTPAD ) ;
12931291 var tx2x = txx + alignShift * ( d . txwidth + HOVERTEXTPAD ) ;
12941292 var offsetX = 0 ;
12951293 var offsetY = d . offset ;
12961294
1297- if ( d . anchor === 'middle' ) {
1295+ if ( anchor === 'middle' ) {
12981296 txx -= d . tx2width / 2 ;
12991297 tx2x += d . txwidth / 2 + HOVERTEXTPAD ;
13001298 }
@@ -1303,7 +1301,7 @@ function alignHoverText(hoverLabels, rotateLabels) {
13031301 offsetX = d . offset * YSHIFTX ;
13041302 }
13051303
1306- g . select ( 'path' ) . attr ( 'd' , d . anchor === 'middle' ?
1304+ g . select ( 'path' ) . attr ( 'd' , anchor === 'middle' ?
13071305 // middle aligned: rect centered on data
13081306 ( 'M-' + ( d . bx / 2 + d . tx2width / 2 ) + ',' + ( offsetY - d . by / 2 ) +
13091307 'h' + d . bx + 'v' + d . by + 'h-' + d . bx + 'Z' ) :
@@ -1316,8 +1314,21 @@ function alignHoverText(hoverLabels, rotateLabels) {
13161314 'V' + ( offsetY - HOVERARROWSIZE ) +
13171315 'Z' ) ) ;
13181316
1319- tx . call ( svgTextUtils . positionText ,
1320- txx + offsetX , offsetY + d . ty0 - d . by / 2 + HOVERTEXTPAD ) ;
1317+ var posX = txx + offsetX ;
1318+ var posY = offsetY + d . ty0 - d . by / 2 + HOVERTEXTPAD ;
1319+ var textAlign = d . textAlign || 'auto' ;
1320+
1321+ if ( textAlign !== 'auto' ) {
1322+ if ( textAlign === 'left' && anchor !== 'start' ) {
1323+ tx . attr ( 'text-anchor' , 'start' ) ;
1324+ posX = - d . bx - HOVERTEXTPAD ;
1325+ } else if ( textAlign === 'right' && anchor !== 'end' ) {
1326+ tx . attr ( 'text-anchor' , 'end' ) ;
1327+ posX = d . bx + HOVERTEXTPAD ;
1328+ }
1329+ }
1330+
1331+ tx . call ( svgTextUtils . positionText , posX , posY ) ;
13211332
13221333 if ( d . tx2width ) {
13231334 g . select ( 'text.name' )
@@ -1364,6 +1375,7 @@ function cleanPoint(d, hovermode) {
13641375 fill ( 'fontSize' , 'hts' , 'hoverlabel.font.size' ) ;
13651376 fill ( 'fontColor' , 'htc' , 'hoverlabel.font.color' ) ;
13661377 fill ( 'nameLength' , 'hnl' , 'hoverlabel.namelength' ) ;
1378+ fill ( 'textAlign' , 'hta' , 'hoverlabel.align' ) ;
13671379
13681380 d . posref = ( hovermode === 'y' || ( hovermode === 'closest' && trace . orientation === 'h' ) ) ?
13691381 ( d . xa . _offset + ( d . x0 + d . x1 ) / 2 ) :
0 commit comments