[Code Style] Use prototypes in inspection bundle

WTD-1482
This commit is contained in:
Victor Woeltjen 2015-08-11 10:00:56 -07:00
parent 140d767026
commit de291ad3b1
2 changed files with 137 additions and 120 deletions

View File

@ -32,90 +32,104 @@ define(
* *
* @memberof platform/commonUI/inspect * @memberof platform/commonUI/inspect
* @constructor * @constructor
* @implements {Gesture}
* @param $timeout Angular's `$timeout` * @param $timeout Angular's `$timeout`
* @param {InfoService} infoService a service which shows info bubbles * @param {InfoService} infoService a service which shows info bubbles
* @param {number} DELAY delay, in milliseconds, before bubble appears * @param {number} delay delay, in milliseconds, before bubble appears
* @param element jqLite-wrapped DOM element * @param element jqLite-wrapped DOM element
* @param {DomainObject} domainObject the domain object for which to * @param {DomainObject} domainObject the domain object for which to
* show information * show information
*/ */
function InfoGesture($timeout, infoService, DELAY, element, domainObject) { function InfoGesture($timeout, infoService, delay, element, domainObject) {
var dismissBubble, var self = this;
pendingBubble,
mousePosition,
scopeOff;
function trackPosition(event) { // Callback functions to preserve the "this" pointer (in the
// Record mouse position, so bubble can be shown at latest // absence of Function.prototype.bind)
// mouse position (not just where the mouse entered) this.showBubbleCallback = function (event) {
mousePosition = [ event.clientX, event.clientY ]; self.showBubble(event);
} };
this.hideBubbleCallback = function (event) {
function hideBubble() { self.hideBubble(event);
// If a bubble is showing, dismiss it };
if (dismissBubble) { this.trackPositionCallback = function (event) {
dismissBubble(); self.trackPosition(event);
element.off('mouseleave', hideBubble); };
dismissBubble = undefined;
}
// If a bubble will be shown on a timeout, cancel that
if (pendingBubble) {
$timeout.cancel(pendingBubble);
element.off('mousemove', trackPosition);
element.off('mouseleave', hideBubble);
pendingBubble = undefined;
}
// Also clear mouse position so we don't have a ton of tiny
// arrays allocated while user mouses over things
mousePosition = undefined;
}
function showBubble(event) {
trackPosition(event);
// Also need to track position during hover
element.on('mousemove', trackPosition);
// Show the bubble, after a suitable delay (if mouse has
// left before this time is up, this will be canceled.)
pendingBubble = $timeout(function () {
dismissBubble = infoService.display(
"info-table",
domainObject.getModel().name,
domainObject.useCapability('metadata'),
mousePosition
);
element.off('mousemove', trackPosition);
pendingBubble = undefined;
}, DELAY);
element.on('mouseleave', hideBubble);
}
// Show bubble (on a timeout) on mouse over
element.on('mouseenter', showBubble);
// Also make sure we dismiss bubble if representation is destroyed // Also make sure we dismiss bubble if representation is destroyed
// before the mouse actually leaves it // before the mouse actually leaves it
scopeOff = element.scope().$on('$destroy', hideBubble); this.scopeOff = element.scope().$on('$destroy', this.hideBubbleCallback);
return { this.element = element;
/** this.$timeout = $timeout;
* Detach any event handlers associated with this gesture. this.infoService = infoService;
* @memberof InfoGesture this.delay = delay;
* @method this.domainObject = domainObject;
* @memberof platform/commonUI/inspect.InfoGesture#
*/ // Show bubble (on a timeout) on mouse over
destroy: function () { element.on('mouseenter', this.showBubbleCallback);
// Dismiss any active bubble...
hideBubble();
// ...and detach listeners
element.off('mouseenter', showBubble);
scopeOff();
}
};
} }
InfoGesture.prototype.trackPosition = function (event) {
// Record mouse position, so bubble can be shown at latest
// mouse position (not just where the mouse entered)
this.mousePosition = [ event.clientX, event.clientY ];
};
InfoGesture.prototype.hideBubble = function () {
// If a bubble is showing, dismiss it
if (this.dismissBubble) {
this.dismissBubble();
this.element.off('mouseleave', this.hideBubbleCallback);
this.dismissBubble = undefined;
}
// If a bubble will be shown on a timeout, cancel that
if (this.pendingBubble) {
this.$timeout.cancel(this.pendingBubble);
this.element.off('mousemove', this.trackPositionCallback);
this.element.off('mouseleave', this.hideBubbleCallback);
this.pendingBubble = undefined;
}
// Also clear mouse position so we don't have a ton of tiny
// arrays allocated while user mouses over things
this.mousePosition = undefined;
};
InfoGesture.prototype.showBubble = function (event) {
var self = this;
this.trackPosition(event);
// Also need to track position during hover
this.element.on('mousemove', this.trackPositionCallback);
// Show the bubble, after a suitable delay (if mouse has
// left before this time is up, this will be canceled.)
this.pendingBubble = this.$timeout(function () {
self.dismissBubble = self.infoService.display(
"info-table",
self.domainObject.getModel().name,
self.domainObject.useCapability('metadata'),
self.mousePosition
);
self.element.off('mousemove', self.trackPositionCallback);
self.pendingBubble = undefined;
}, this.delay);
this.element.on('mouseleave', this.hideBubbleCallback);
};
/**
* Detach any event handlers associated with this gesture.
* @method
*/
InfoGesture.prototype.destroy = function () {
// Dismiss any active bubble...
this.hideBubble();
// ...and detach listeners
this.element.off('mouseenter', this.showBubbleCallback);
this.scopeOff();
};
return InfoGesture; return InfoGesture;
} }

View File

@ -35,61 +35,64 @@ define(
* @constructor * @constructor
*/ */
function InfoService($compile, $document, $window, $rootScope) { function InfoService($compile, $document, $window, $rootScope) {
this.$compile = $compile;
this.$document = $document;
this.$window = $window;
this.$rootScope = $rootScope;
}
function display(templateKey, title, content, position) { /**
var body = $document.find('body'), * Display an info bubble at the specified location.
scope = $rootScope.$new(), * @param {string} templateKey template to place in bubble
winDim = [$window.innerWidth, $window.innerHeight], * @param {string} title title for the bubble
bubbleSpaceLR = InfoConstants.BUBBLE_MARGIN_LR + InfoConstants.BUBBLE_MAX_WIDTH, * @param {*} content content to pass to the template, via
goLeft = position[0] > (winDim[0] - bubbleSpaceLR), * `ng-model`
goUp = position[1] > (winDim[1] / 2), * @param {number[]} x,y position of the info bubble, in
bubble; * pixel coordinates.
* @returns {Function} a function that may be invoked to
* dismiss the info bubble
*/
InfoService.prototype.display = function (templateKey, title, content, position) {
var $compile = this.$compile,
$document = this.$document,
$window = this.$window,
$rootScope = this.$rootScope,
body = $document.find('body'),
scope = $rootScope.$new(),
winDim = [$window.innerWidth, $window.innerHeight],
bubbleSpaceLR = InfoConstants.BUBBLE_MARGIN_LR + InfoConstants.BUBBLE_MAX_WIDTH,
goLeft = position[0] > (winDim[0] - bubbleSpaceLR),
goUp = position[1] > (winDim[1] / 2),
bubble;
// Pass model & container parameters into the scope // Pass model & container parameters into the scope
scope.bubbleModel = content; scope.bubbleModel = content;
scope.bubbleTemplate = templateKey; scope.bubbleTemplate = templateKey;
scope.bubbleLayout = (goUp ? 'arw-btm' : 'arw-top') + ' ' + scope.bubbleLayout = (goUp ? 'arw-btm' : 'arw-top') + ' ' +
(goLeft ? 'arw-right' : 'arw-left'); (goLeft ? 'arw-right' : 'arw-left');
scope.bubbleTitle = title; scope.bubbleTitle = title;
// Create the context menu // Create the context menu
bubble = $compile(BUBBLE_TEMPLATE)(scope); bubble = $compile(BUBBLE_TEMPLATE)(scope);
// Position the bubble // Position the bubble
bubble.css('position', 'absolute'); bubble.css('position', 'absolute');
if (goLeft) { if (goLeft) {
bubble.css('right', (winDim[0] - position[0] + OFFSET[0]) + 'px'); bubble.css('right', (winDim[0] - position[0] + OFFSET[0]) + 'px');
} else { } else {
bubble.css('left', position[0] + OFFSET[0] + 'px'); bubble.css('left', position[0] + OFFSET[0] + 'px');
} }
if (goUp) { if (goUp) {
bubble.css('bottom', (winDim[1] - position[1] + OFFSET[1]) + 'px'); bubble.css('bottom', (winDim[1] - position[1] + OFFSET[1]) + 'px');
} else { } else {
bubble.css('top', position[1] + OFFSET[1] + 'px'); bubble.css('top', position[1] + OFFSET[1] + 'px');
}
// Add the menu to the body
body.append(bubble);
// Return a function to dismiss the bubble
return function () { bubble.remove(); };
} }
return { // Add the menu to the body
/** body.append(bubble);
* Display an info bubble at the specified location.
* @param {string} templateKey template to place in bubble // Return a function to dismiss the bubble
* @param {string} title title for the bubble return function () { bubble.remove(); };
* @param {*} content content to pass to the template, via
* `ng-model`
* @param {number[]} x,y position of the info bubble, in
* pixel coordinates.
* @returns {Function} a function that may be invoked to
* dismiss the info bubble
* @memberof platform/commonUI/inspect.InfoService#
*/
display: display
};
} }
return InfoService; return InfoService;