@@ -110,19 +110,43 @@ parseDuration = (duration) ->
110110offsetDate = (date , seconds ) ->
111111 return new Date (date .getTime () + seconds * 1000 )
112112
113- centerTooltipOn = (tooltip , target , dir = ' center' , offset = [0 , 0 ]) ->
113+
114+ findParentByClass = (element , className ) ->
115+ # traverse up the DOM tree until requested parent node is found
116+ while element .classList
117+ if element .classList .contains (className)
118+ return element
119+ element = element .parentNode
120+
121+
122+ centerTooltipOn = (tooltip , target , dir = ' center' , offset = [0 , 0 ], viewportClassName = ' timeslider' ) ->
114123 rect = target .getBoundingClientRect ()
115124 tooltipRect = tooltip[0 ][0 ].getBoundingClientRect ()
125+
126+ viewport = findParentByClass (target, viewportClassName)
127+
128+ if viewport
129+ # clip the x-axis rectangle bounds to the viewport extent
130+ # to make the tooltip always visible
131+ viewportRect = viewport .getBoundingClientRect ()
132+ xLeft = Math .max (rect .left , viewportRect .left )
133+ xRight = Math .min (rect .right , viewportRect .right )
134+ else
135+ # default to the rectangle bounds if the viewport cannot be found
136+ xLeft = rect .left
137+ xRight = rect .right
138+
116139 if dir == ' left'
117- xOff = rect . left
140+ xOff = xLeft
118141 else if dir == ' right'
119- xOff = rect . right
142+ xOff = xRight
120143 else
121- xOff = rect . left + rect . width / 2
144+ xOff = xLeft + (xRight - xLeft) / 2
122145 tooltip
123146 .style (' left' , xOff - tooltipRect .width / 2 + offset[0 ] + " px" )
124147 .style (' top' , (rect .top - tooltipRect .height ) + offset[1 ] + " px" )
125148
149+
126150module .exports =
127151 split : split
128152 bisect : bisect
0 commit comments