I apologize in advance - I don't post code much (also note that it is an old application and thus is not written with AMD-style references).
The premise for my fix is that the built-in zoom functions work well - the problem manifests when using a secondary function to zoom by a large degree. In my case, zooming to a selected feature/graphic.
This function is an intermediate tool that uses map.centerAndZoom to zoom to the indicated extent, but only if the extent is within a zoom threshold, otherwise, it will still center the extent, but only take the level down 3 more levels (I know this part is arbitrary). If you wanted to do a REALLY good job, you would put an interval object in to zoom partially, wait a second, and then zoom again until reaching the full-zoom. My application didn't require that much zooming though.
function zoomThrottle (myFeatureExtent) {
// limits the change in level to prevent zoom animation menory leak problems
var zoomFactorX = (map.extent.xmax - map.extent.xmin)/(myFeatureExtent.xmax - myFeatureExtent.xmin);
var zoomFactorY = (map.extent.ymax - map.extent.ymin)/(myFeatureExtent.ymax - myFeatureExtent.ymin);
var newCenterPoint = new esri.geometry.Point((myFeatureExtent.xmin + myFeatureExtent.xmax)/2, (myFeatureExtent.ymin + myFeatureExtent.ymax)/2, new esri.SpatialReference({wkid: myFeatureExtent.spatialReference.wkid}))
var newScaleFactor = 0;
if (zoomFactorX > zoomFactorY) {
newScaleFactor = map.getScale()/zoomFactorX;
} else {
newScaleFactor = map.getScale()/zoomFactorY;
}
var newLevel = lods[lods.length-1].level;
for (var ii = 0; ii < boundingLods.length; ii ++) {
if (newScaleFactor < boundingLods[ii].ceiling && newScaleFactor > boundingLods[ii].floor) {
newLevel = boundingLods[ii].level;
break;
}
}
// lookup level
var scaleFactorCeiling = 100;
if (lods[map.getLevel()].scale/lods[newLevel].scale > scaleFactorCeiling) {
newLevel = map.getLevel() + 3;
}
map.centerAndZoom(newCenterPoint, newLevel);
}