I have an whose width is 100% of its container. When the container is resized, I update the linear xScale.range() to represent the new
It looks like the best strategy is to cache the scale and translate values, reset, then reapply. For the record, this code (within my resize handler) roughly shows my solution:
// Cache scale
var cacheScale = zoom.scale();
// Cache translate
var cacheTranslate = zoom.translate();
// Cache translate values as percentages/ratio of the full width
var cacheTranslatePerc = zoom.translate().map( function( v, i, a )
{
return (v * -1) / getFullWidth();
} );
// Manually reset the zoom
zoom.scale( 1 ).translate( [0, 0] );
// Update range values based on resized container dimensions
xScale.range( [0, myResizedContainerWidth] );
// Apply the updated xScale to the zoom
zoom.x( xScale );
// Revert the scale back to our cached value
zoom.scale( cacheScale );
// Overwrite the x value of cacheTranslate based on our cached percentage
cacheTranslate[0] = -(getFullWidth() * cacheTranslatePerc[0]);
// Finally apply the updated translate
zoom.translate( cacheTranslate );
function getFullWidth()
{
return xScale.range()[1] * zoom.scale();
}