Merge pull request #955 from nasa/timeline-zoom-936

[Timeline] Improve zoom behaviors
This commit is contained in:
Andrew Henry
2016-05-25 16:58:20 -07:00
4 changed files with 108 additions and 48 deletions

View File

@@ -32,16 +32,26 @@ define(
var zoomLevels = ZOOM_CONFIGURATION.levels || [1000],
zoomIndex = Math.floor(zoomLevels.length / 2),
tickWidth = ZOOM_CONFIGURATION.width || 200,
bounds = { x: 0, width: tickWidth },
duration = 86400000; // Default duration in view
// Round a duration to a larger value, to ensure space for editing
function roundDuration(value) {
// Ensure there's always an extra day or so
var sz = zoomLevels[zoomLevels.length - 1];
var tickCount = bounds.width / tickWidth,
sz = zoomLevels[zoomLevels.length - 1] * tickCount;
value *= 1.25; // Add 25% padding to start
return Math.ceil(value / sz) * sz;
}
function toMillis(pixels) {
return (pixels / tickWidth) * zoomLevels[zoomIndex];
}
function toPixels(millis) {
return tickWidth * millis / zoomLevels[zoomIndex];
}
// Get/set zoom level
function setZoomLevel(level) {
if (!isNaN(level)) {
@@ -53,20 +63,27 @@ define(
}
}
// Persist current zoom level
function storeZoom() {
var isEditMode = $scope.commit &&
$scope.domainObject &&
$scope.domainObject.hasCapability('editor') &&
$scope.domainObject.getCapability('editor').inEditContext();
if (isEditMode) {
$scope.configuration = $scope.configuration || {};
$scope.configuration.zoomLevel = zoomIndex;
$scope.commit();
function initializeZoomFromTimespan(timespan) {
var timelineDuration = timespan.getDuration();
zoomIndex = 0;
while (toMillis(bounds.width) < timelineDuration &&
zoomIndex < zoomLevels.length - 1) {
zoomIndex += 1;
}
bounds.x = toPixels(timespan.getStart());
}
function initializeZoom() {
if ($scope.domainObject) {
$scope.domainObject.useCapability('timespan')
.then(initializeZoomFromTimespan);
}
}
$scope.$watch("configuration.zoomLevel", setZoomLevel);
$scope.$watch("scroll", function (scroll) {
bounds = scroll;
});
$scope.$watch("domainObject", initializeZoom);
return {
/**
@@ -83,27 +100,29 @@ define(
zoom: function (amount) {
// Update the zoom level if called with an argument
if (arguments.length > 0 && !isNaN(amount)) {
var center = this.toMillis(bounds.x + bounds.width / 2);
setZoomLevel(zoomIndex + amount);
storeZoom(zoomIndex);
bounds.x = this.toPixels(center) - bounds.width / 2;
}
return zoomLevels[zoomIndex];
},
/**
* Set the zoom level to fit the bounds of the timeline
* being viewed.
*/
fit: initializeZoom,
/**
* Get the width, in pixels, of a specific time duration at
* the current zoom level.
* @returns {number} the number of pixels
*/
toPixels: function (millis) {
return tickWidth * millis / zoomLevels[zoomIndex];
},
toPixels: toPixels,
/**
* Get the time duration, in milliseconds, occupied by the
* width (specified in pixels) at the current zoom level.
* @returns {number} the number of pixels
*/
toMillis: function (pixels) {
return (pixels / tickWidth) * zoomLevels[zoomIndex];
},
toMillis: toMillis,
/**
* Get or set the current displayed duration. If used as a
* setter, this will typically be rounded up to ensure extra