1 new commit in galaxy-central: https://bitbucket.org/galaxy/galaxy-central/commits/8e98c3d9b9a8/ Changeset: 8e98c3d9b9a8 User: carlfeberhard Date: 2014-12-08 21:34:09+00:00 Summary: Client build: modularize mode-button plugin from ui.js; update history/multi-view.js and history/view.mako Affected #: 10 files diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 client/galaxy/scripts/jq-plugins/ui/mode-button.js --- /dev/null +++ b/client/galaxy/scripts/jq-plugins/ui/mode-button.js @@ -0,0 +1,191 @@ +// from: https://raw.githubusercontent.com/umdjs/umd/master/jqueryPlugin.js +// Uses AMD or browser globals to create a jQuery plugin. +(function (factory) { + if (typeof define === 'function' && define.amd) { + //TODO: So...this turns out to be an all or nothing thing. If I load jQuery in the define below, it will + // (of course) wipe the old jquery *and all the plugins loaded into it*. So the define below *is still + // relying on jquery being loaded globally* in order to preserve plugins. + define([], factory); + } else { + // Browser globals + factory(jQuery); + } + +}(function () { + + /** Multi 'mode' button (or any element really) that changes the html + * contents of itself when clicked. Pass in an ordered list of + * objects with 'html' and (optional) onclick functions. + * + * When clicked in a particular node, the onclick function will + * be called (with the element as this) and the element will + * switch to the next mode, replacing its html content with + * that mode's html. + * + * If there is no next mode, the element will switch back to + * the first mode. + * @example: + * $( '.myElement' ).modeButton({ + * modes : [ + * { + * mode: 'bler', + * html: '<h5>Bler</h5>', + * onclick : function(){ + * $( 'body' ).css( 'background-color', 'red' ); + * } + * }, + * { + * mode: 'bloo', + * html: '<h4>Bloo</h4>', + * onclick : function(){ + * $( 'body' ).css( 'background-color', 'blue' ); + * } + * }, + * { + * mode: 'blah', + * html: '<h3>Blah</h3>', + * onclick : function(){ + * $( 'body' ).css( 'background-color', 'grey' ); + * } + * }, + * ] + * }); + * $( '.myElement' ).modeButton( 'callModeFn', 'bler' ); + */ + /** constructor */ + function ModeButton( element, options ){ + this.currModeIndex = 0; + return this._init( element, options ); + } + + /** html5 data key to store this object inside an element */ + ModeButton.prototype.DATA_KEY = 'mode-button'; + /** default options */ + ModeButton.prototype.defaults = { + switchModesOnClick : true + }; + + // ---- private interface + /** set up options, intial mode, and the click handler */ + ModeButton.prototype._init = function _init( element, options ){ + //console.debug( 'ModeButton._init:', element, options ); + options = options || {}; + this.$element = $( element ); + this.options = $.extend( true, {}, this.defaults, options ); + if( !options.modes ){ + throw new Error( 'ModeButton requires a "modes" array' ); + } + + var modeButton = this; + this.$element.click( function _ModeButtonClick( event ){ + // call the curr mode fn + modeButton.callModeFn(); + // inc the curr mode index + if( modeButton.options.switchModesOnClick ){ modeButton._incModeIndex(); } + // set the element html + $( this ).html( modeButton.options.modes[ modeButton.currModeIndex ].html ); + }); + return this.reset(); + }; + /** increment the mode index to the next in the array, looping back to zero if at the last */ + ModeButton.prototype._incModeIndex = function _incModeIndex(){ + this.currModeIndex += 1; + if( this.currModeIndex >= this.options.modes.length ){ + this.currModeIndex = 0; + } + return this; + }; + /** get the mode index in the modes array for the given key (mode name) */ + ModeButton.prototype._getModeIndex = function _getModeIndex( modeKey ){ + for( var i=0; i<this.options.modes.length; i+=1 ){ + if( this.options.modes[ i ].mode === modeKey ){ return i; } + } + throw new Error( 'mode not found: ' + modeKey ); + }; + /** set the current mode to the one with the given index and set button html */ + ModeButton.prototype._setModeByIndex = function _setModeByIndex( index ){ + var newMode = this.options.modes[ index ]; + if( !newMode ){ + throw new Error( 'mode index not found: ' + index ); + } + this.currModeIndex = index; + if( newMode.html ){ + this.$element.html( newMode.html ); + } + return this; + }; + + // ---- public interface + /** get the current mode object (not just the mode name) */ + ModeButton.prototype.currentMode = function currentMode(){ + return this.options.modes[ this.currModeIndex ]; + }; + /** return the mode key of the current mode */ + ModeButton.prototype.current = function current(){ + // sugar for returning mode name + return this.currentMode().mode; + }; + /** get the mode with the given modeKey or the current mode if modeKey is undefined */ + ModeButton.prototype.getMode = function getMode( modeKey ){ + if( !modeKey ){ return this.currentMode(); } + return this.options.modes[( this._getModeIndex( modeKey ) )]; + }; + /** T/F if the button has the given mode */ + ModeButton.prototype.hasMode = function hasMode( modeKey ){ + try { + return !!this.getMode( modeKey ); + } catch( err ){} + return false; + }; + /** set the current mode to the mode with the given name */ + ModeButton.prototype.setMode = function setMode( modeKey ){ + return this._setModeByIndex( this._getModeIndex( modeKey ) ); + }; + /** reset to the initial mode */ + ModeButton.prototype.reset = function reset(){ + this.currModeIndex = 0; + if( this.options.initialMode ){ + this.currModeIndex = this._getModeIndex( this.options.initialMode ); + } + return this._setModeByIndex( this.currModeIndex ); + }; + /** manually call the click handler of the given mode */ + ModeButton.prototype.callModeFn = function callModeFn( modeKey ){ + var modeFn = this.getMode( modeKey ).onclick; + if( modeFn && $.type( modeFn === 'function' ) ){ + // call with the element as context (std jquery pattern) + return modeFn.call( this.$element.get(0) ); + } + return undefined; + }; + + // as jq plugin + $.fn.modeButton = function $modeButton( options ){ + if( !this.size() ){ return this; } + + //TODO: does map still work with jq multi selection (i.e. $( '.class-for-many-btns' ).modeButton)? + if( $.type( options ) === 'object' ){ + return this.map( function(){ + var $this = $( this ); + $this.data( 'mode-button', new ModeButton( $this, options ) ); + return this; + }); + } + + var $first = $( this[0] ), + button = $first.data( 'mode-button' ); + + if( !button ){ + throw new Error( 'modeButton needs an options object or string name of a function' ); + } + + if( button && $.type( options ) === 'string' ){ + var fnName = options; + if( button && $.type( button[ fnName ] ) === 'function' ){ + return button[ fnName ].apply( button, $.makeArray( arguments ).slice( 1 ) ); + } + } + return button; + }; + +})); diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 client/galaxy/scripts/mvc/history/multi-panel.js --- a/client/galaxy/scripts/mvc/history/multi-panel.js +++ b/client/galaxy/scripts/mvc/history/multi-panel.js @@ -2,7 +2,8 @@ "mvc/history/history-model", "mvc/history/history-panel-edit", "mvc/base-mvc", - "utils/ajax-queue" + "utils/ajax-queue", + "jq-plugins/ui/mode-button" ], function( HISTORY_MODEL, HPANEL_EDIT, baseMVC, ajaxQueue ){ window.HISTORY_MODEL = HISTORY_MODEL; //============================================================================== diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 client/galaxy/scripts/mvc/ui.js --- a/client/galaxy/scripts/mvc/ui.js +++ b/client/galaxy/scripts/mvc/ui.js @@ -749,184 +749,3 @@ } }); }()); - - -//============================================================================== -(function(){ - /** Multi 'mode' button (or any element really) that changes the html - * contents of itself when clicked. Pass in an ordered list of - * objects with 'html' and (optional) onclick functions. - * - * When clicked in a particular node, the onclick function will - * be called (with the element as this) and the element will - * switch to the next mode, replacing its html content with - * that mode's html. - * - * If there is no next mode, the element will switch back to - * the first mode. - * @example: - * $( '.myElement' ).modeButton({ - * modes : [ - * { - * mode: 'bler', - * html: '<h5>Bler</h5>', - * onclick : function(){ - * $( 'body' ).css( 'background-color', 'red' ); - * } - * }, - * { - * mode: 'bloo', - * html: '<h4>Bloo</h4>', - * onclick : function(){ - * $( 'body' ).css( 'background-color', 'blue' ); - * } - * }, - * { - * mode: 'blah', - * html: '<h3>Blah</h3>', - * onclick : function(){ - * $( 'body' ).css( 'background-color', 'grey' ); - * } - * }, - * ] - * }); - * $( '.myElement' ).modeButton( 'callModeFn', 'bler' ); - */ - /** constructor */ - function ModeButton( element, options ){ - this.currModeIndex = 0; - return this._init( element, options ); - } - - /** html5 data key to store this object inside an element */ - ModeButton.prototype.DATA_KEY = 'mode-button'; - /** default options */ - ModeButton.prototype.defaults = { - switchModesOnClick : true - }; - - // ---- private interface - /** set up options, intial mode, and the click handler */ - ModeButton.prototype._init = function _init( element, options ){ - //console.debug( 'ModeButton._init:', element, options ); - options = options || {}; - this.$element = $( element ); - this.options = jQuery.extend( true, {}, this.defaults, options ); - if( !options.modes ){ - throw new Error( 'ModeButton requires a "modes" array' ); - } - - var modeButton = this; - this.$element.click( function _ModeButtonClick( event ){ - // call the curr mode fn - modeButton.callModeFn(); - // inc the curr mode index - if( modeButton.options.switchModesOnClick ){ modeButton._incModeIndex(); } - // set the element html - $( this ).html( modeButton.options.modes[ modeButton.currModeIndex ].html ); - }); - return this.reset(); - }; - /** increment the mode index to the next in the array, looping back to zero if at the last */ - ModeButton.prototype._incModeIndex = function _incModeIndex(){ - this.currModeIndex += 1; - if( this.currModeIndex >= this.options.modes.length ){ - this.currModeIndex = 0; - } - return this; - }; - /** get the mode index in the modes array for the given key (mode name) */ - ModeButton.prototype._getModeIndex = function _getModeIndex( modeKey ){ - for( var i=0; i<this.options.modes.length; i+=1 ){ - if( this.options.modes[ i ].mode === modeKey ){ return i; } - } - throw new Error( 'mode not found: ' + modeKey ); - }; - /** set the current mode to the one with the given index and set button html */ - ModeButton.prototype._setModeByIndex = function _setModeByIndex( index ){ - var newMode = this.options.modes[ index ]; - if( !newMode ){ - throw new Error( 'mode index not found: ' + index ); - } - this.currModeIndex = index; - if( newMode.html ){ - this.$element.html( newMode.html ); - } - return this; - }; - - // ---- public interface - /** get the current mode object (not just the mode name) */ - ModeButton.prototype.currentMode = function currentMode(){ - return this.options.modes[ this.currModeIndex ]; - }; - /** return the mode key of the current mode */ - ModeButton.prototype.current = function current(){ - // sugar for returning mode name - return this.currentMode().mode; - }; - /** get the mode with the given modeKey or the current mode if modeKey is undefined */ - ModeButton.prototype.getMode = function getMode( modeKey ){ - if( !modeKey ){ return this.currentMode(); } - return this.options.modes[( this._getModeIndex( modeKey ) )]; - }; - /** T/F if the button has the given mode */ - ModeButton.prototype.hasMode = function hasMode( modeKey ){ - try { - return !!this.getMode( modeKey ); - } catch( err ){} - return false; - }; - /** set the current mode to the mode with the given name */ - ModeButton.prototype.setMode = function setMode( modeKey ){ - return this._setModeByIndex( this._getModeIndex( modeKey ) ); - }; - /** reset to the initial mode */ - ModeButton.prototype.reset = function reset(){ - this.currModeIndex = 0; - if( this.options.initialMode ){ - this.currModeIndex = this._getModeIndex( this.options.initialMode ); - } - return this._setModeByIndex( this.currModeIndex ); - }; - /** manually call the click handler of the given mode */ - ModeButton.prototype.callModeFn = function callModeFn( modeKey ){ - var modeFn = this.getMode( modeKey ).onclick; - if( modeFn && jQuery.type( modeFn === 'function' ) ){ - // call with the element as context (std jquery pattern) - return modeFn.call( this.$element.get(0) ); - } - return undefined; - }; - - // as jq plugin - jQuery.fn.extend({ - modeButton : function $modeButton( options ){ - if( !this.size() ){ return this; } - - //TODO: does map still work with jq multi selection (i.e. $( '.class-for-many-btns' ).modeButton)? - if( jQuery.type( options ) === 'object' ){ - return this.map( function(){ - var $this = $( this ); - $this.data( 'mode-button', new ModeButton( $this, options ) ); - return this; - }); - } - - var $first = $( this[0] ), - button = $first.data( 'mode-button' ); - - if( !button ){ - throw new Error( 'modeButton needs an options object or string name of a function' ); - } - - if( button && jQuery.type( options ) === 'string' ){ - var fnName = options; - if( button && jQuery.type( button[ fnName ] ) === 'function' ){ - return button[ fnName ].apply( button, jQuery.makeArray( arguments ).slice( 1 ) ); - } - } - return button; - } - }); -}()); diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 static/scripts/jq-plugins/ui/mode-button.js --- /dev/null +++ b/static/scripts/jq-plugins/ui/mode-button.js @@ -0,0 +1,191 @@ +// from: https://raw.githubusercontent.com/umdjs/umd/master/jqueryPlugin.js +// Uses AMD or browser globals to create a jQuery plugin. +(function (factory) { + if (typeof define === 'function' && define.amd) { + //TODO: So...this turns out to be an all or nothing thing. If I load jQuery in the define below, it will + // (of course) wipe the old jquery *and all the plugins loaded into it*. So the define below *is still + // relying on jquery being loaded globally* in order to preserve plugins. + define([], factory); + } else { + // Browser globals + factory(jQuery); + } + +}(function () { + + /** Multi 'mode' button (or any element really) that changes the html + * contents of itself when clicked. Pass in an ordered list of + * objects with 'html' and (optional) onclick functions. + * + * When clicked in a particular node, the onclick function will + * be called (with the element as this) and the element will + * switch to the next mode, replacing its html content with + * that mode's html. + * + * If there is no next mode, the element will switch back to + * the first mode. + * @example: + * $( '.myElement' ).modeButton({ + * modes : [ + * { + * mode: 'bler', + * html: '<h5>Bler</h5>', + * onclick : function(){ + * $( 'body' ).css( 'background-color', 'red' ); + * } + * }, + * { + * mode: 'bloo', + * html: '<h4>Bloo</h4>', + * onclick : function(){ + * $( 'body' ).css( 'background-color', 'blue' ); + * } + * }, + * { + * mode: 'blah', + * html: '<h3>Blah</h3>', + * onclick : function(){ + * $( 'body' ).css( 'background-color', 'grey' ); + * } + * }, + * ] + * }); + * $( '.myElement' ).modeButton( 'callModeFn', 'bler' ); + */ + /** constructor */ + function ModeButton( element, options ){ + this.currModeIndex = 0; + return this._init( element, options ); + } + + /** html5 data key to store this object inside an element */ + ModeButton.prototype.DATA_KEY = 'mode-button'; + /** default options */ + ModeButton.prototype.defaults = { + switchModesOnClick : true + }; + + // ---- private interface + /** set up options, intial mode, and the click handler */ + ModeButton.prototype._init = function _init( element, options ){ + //console.debug( 'ModeButton._init:', element, options ); + options = options || {}; + this.$element = $( element ); + this.options = $.extend( true, {}, this.defaults, options ); + if( !options.modes ){ + throw new Error( 'ModeButton requires a "modes" array' ); + } + + var modeButton = this; + this.$element.click( function _ModeButtonClick( event ){ + // call the curr mode fn + modeButton.callModeFn(); + // inc the curr mode index + if( modeButton.options.switchModesOnClick ){ modeButton._incModeIndex(); } + // set the element html + $( this ).html( modeButton.options.modes[ modeButton.currModeIndex ].html ); + }); + return this.reset(); + }; + /** increment the mode index to the next in the array, looping back to zero if at the last */ + ModeButton.prototype._incModeIndex = function _incModeIndex(){ + this.currModeIndex += 1; + if( this.currModeIndex >= this.options.modes.length ){ + this.currModeIndex = 0; + } + return this; + }; + /** get the mode index in the modes array for the given key (mode name) */ + ModeButton.prototype._getModeIndex = function _getModeIndex( modeKey ){ + for( var i=0; i<this.options.modes.length; i+=1 ){ + if( this.options.modes[ i ].mode === modeKey ){ return i; } + } + throw new Error( 'mode not found: ' + modeKey ); + }; + /** set the current mode to the one with the given index and set button html */ + ModeButton.prototype._setModeByIndex = function _setModeByIndex( index ){ + var newMode = this.options.modes[ index ]; + if( !newMode ){ + throw new Error( 'mode index not found: ' + index ); + } + this.currModeIndex = index; + if( newMode.html ){ + this.$element.html( newMode.html ); + } + return this; + }; + + // ---- public interface + /** get the current mode object (not just the mode name) */ + ModeButton.prototype.currentMode = function currentMode(){ + return this.options.modes[ this.currModeIndex ]; + }; + /** return the mode key of the current mode */ + ModeButton.prototype.current = function current(){ + // sugar for returning mode name + return this.currentMode().mode; + }; + /** get the mode with the given modeKey or the current mode if modeKey is undefined */ + ModeButton.prototype.getMode = function getMode( modeKey ){ + if( !modeKey ){ return this.currentMode(); } + return this.options.modes[( this._getModeIndex( modeKey ) )]; + }; + /** T/F if the button has the given mode */ + ModeButton.prototype.hasMode = function hasMode( modeKey ){ + try { + return !!this.getMode( modeKey ); + } catch( err ){} + return false; + }; + /** set the current mode to the mode with the given name */ + ModeButton.prototype.setMode = function setMode( modeKey ){ + return this._setModeByIndex( this._getModeIndex( modeKey ) ); + }; + /** reset to the initial mode */ + ModeButton.prototype.reset = function reset(){ + this.currModeIndex = 0; + if( this.options.initialMode ){ + this.currModeIndex = this._getModeIndex( this.options.initialMode ); + } + return this._setModeByIndex( this.currModeIndex ); + }; + /** manually call the click handler of the given mode */ + ModeButton.prototype.callModeFn = function callModeFn( modeKey ){ + var modeFn = this.getMode( modeKey ).onclick; + if( modeFn && $.type( modeFn === 'function' ) ){ + // call with the element as context (std jquery pattern) + return modeFn.call( this.$element.get(0) ); + } + return undefined; + }; + + // as jq plugin + $.fn.modeButton = function $modeButton( options ){ + if( !this.size() ){ return this; } + + //TODO: does map still work with jq multi selection (i.e. $( '.class-for-many-btns' ).modeButton)? + if( $.type( options ) === 'object' ){ + return this.map( function(){ + var $this = $( this ); + $this.data( 'mode-button', new ModeButton( $this, options ) ); + return this; + }); + } + + var $first = $( this[0] ), + button = $first.data( 'mode-button' ); + + if( !button ){ + throw new Error( 'modeButton needs an options object or string name of a function' ); + } + + if( button && $.type( options ) === 'string' ){ + var fnName = options; + if( button && $.type( button[ fnName ] ) === 'function' ){ + return button[ fnName ].apply( button, $.makeArray( arguments ).slice( 1 ) ); + } + } + return button; + }; + +})); diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 static/scripts/mvc/history/multi-panel.js --- a/static/scripts/mvc/history/multi-panel.js +++ b/static/scripts/mvc/history/multi-panel.js @@ -2,7 +2,8 @@ "mvc/history/history-model", "mvc/history/history-panel-edit", "mvc/base-mvc", - "utils/ajax-queue" + "utils/ajax-queue", + "jq-plugins/ui/mode-button" ], function( HISTORY_MODEL, HPANEL_EDIT, baseMVC, ajaxQueue ){ window.HISTORY_MODEL = HISTORY_MODEL; //============================================================================== diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 static/scripts/mvc/ui.js --- a/static/scripts/mvc/ui.js +++ b/static/scripts/mvc/ui.js @@ -749,184 +749,3 @@ } }); }()); - - -//============================================================================== -(function(){ - /** Multi 'mode' button (or any element really) that changes the html - * contents of itself when clicked. Pass in an ordered list of - * objects with 'html' and (optional) onclick functions. - * - * When clicked in a particular node, the onclick function will - * be called (with the element as this) and the element will - * switch to the next mode, replacing its html content with - * that mode's html. - * - * If there is no next mode, the element will switch back to - * the first mode. - * @example: - * $( '.myElement' ).modeButton({ - * modes : [ - * { - * mode: 'bler', - * html: '<h5>Bler</h5>', - * onclick : function(){ - * $( 'body' ).css( 'background-color', 'red' ); - * } - * }, - * { - * mode: 'bloo', - * html: '<h4>Bloo</h4>', - * onclick : function(){ - * $( 'body' ).css( 'background-color', 'blue' ); - * } - * }, - * { - * mode: 'blah', - * html: '<h3>Blah</h3>', - * onclick : function(){ - * $( 'body' ).css( 'background-color', 'grey' ); - * } - * }, - * ] - * }); - * $( '.myElement' ).modeButton( 'callModeFn', 'bler' ); - */ - /** constructor */ - function ModeButton( element, options ){ - this.currModeIndex = 0; - return this._init( element, options ); - } - - /** html5 data key to store this object inside an element */ - ModeButton.prototype.DATA_KEY = 'mode-button'; - /** default options */ - ModeButton.prototype.defaults = { - switchModesOnClick : true - }; - - // ---- private interface - /** set up options, intial mode, and the click handler */ - ModeButton.prototype._init = function _init( element, options ){ - //console.debug( 'ModeButton._init:', element, options ); - options = options || {}; - this.$element = $( element ); - this.options = jQuery.extend( true, {}, this.defaults, options ); - if( !options.modes ){ - throw new Error( 'ModeButton requires a "modes" array' ); - } - - var modeButton = this; - this.$element.click( function _ModeButtonClick( event ){ - // call the curr mode fn - modeButton.callModeFn(); - // inc the curr mode index - if( modeButton.options.switchModesOnClick ){ modeButton._incModeIndex(); } - // set the element html - $( this ).html( modeButton.options.modes[ modeButton.currModeIndex ].html ); - }); - return this.reset(); - }; - /** increment the mode index to the next in the array, looping back to zero if at the last */ - ModeButton.prototype._incModeIndex = function _incModeIndex(){ - this.currModeIndex += 1; - if( this.currModeIndex >= this.options.modes.length ){ - this.currModeIndex = 0; - } - return this; - }; - /** get the mode index in the modes array for the given key (mode name) */ - ModeButton.prototype._getModeIndex = function _getModeIndex( modeKey ){ - for( var i=0; i<this.options.modes.length; i+=1 ){ - if( this.options.modes[ i ].mode === modeKey ){ return i; } - } - throw new Error( 'mode not found: ' + modeKey ); - }; - /** set the current mode to the one with the given index and set button html */ - ModeButton.prototype._setModeByIndex = function _setModeByIndex( index ){ - var newMode = this.options.modes[ index ]; - if( !newMode ){ - throw new Error( 'mode index not found: ' + index ); - } - this.currModeIndex = index; - if( newMode.html ){ - this.$element.html( newMode.html ); - } - return this; - }; - - // ---- public interface - /** get the current mode object (not just the mode name) */ - ModeButton.prototype.currentMode = function currentMode(){ - return this.options.modes[ this.currModeIndex ]; - }; - /** return the mode key of the current mode */ - ModeButton.prototype.current = function current(){ - // sugar for returning mode name - return this.currentMode().mode; - }; - /** get the mode with the given modeKey or the current mode if modeKey is undefined */ - ModeButton.prototype.getMode = function getMode( modeKey ){ - if( !modeKey ){ return this.currentMode(); } - return this.options.modes[( this._getModeIndex( modeKey ) )]; - }; - /** T/F if the button has the given mode */ - ModeButton.prototype.hasMode = function hasMode( modeKey ){ - try { - return !!this.getMode( modeKey ); - } catch( err ){} - return false; - }; - /** set the current mode to the mode with the given name */ - ModeButton.prototype.setMode = function setMode( modeKey ){ - return this._setModeByIndex( this._getModeIndex( modeKey ) ); - }; - /** reset to the initial mode */ - ModeButton.prototype.reset = function reset(){ - this.currModeIndex = 0; - if( this.options.initialMode ){ - this.currModeIndex = this._getModeIndex( this.options.initialMode ); - } - return this._setModeByIndex( this.currModeIndex ); - }; - /** manually call the click handler of the given mode */ - ModeButton.prototype.callModeFn = function callModeFn( modeKey ){ - var modeFn = this.getMode( modeKey ).onclick; - if( modeFn && jQuery.type( modeFn === 'function' ) ){ - // call with the element as context (std jquery pattern) - return modeFn.call( this.$element.get(0) ); - } - return undefined; - }; - - // as jq plugin - jQuery.fn.extend({ - modeButton : function $modeButton( options ){ - if( !this.size() ){ return this; } - - //TODO: does map still work with jq multi selection (i.e. $( '.class-for-many-btns' ).modeButton)? - if( jQuery.type( options ) === 'object' ){ - return this.map( function(){ - var $this = $( this ); - $this.data( 'mode-button', new ModeButton( $this, options ) ); - return this; - }); - } - - var $first = $( this[0] ), - button = $first.data( 'mode-button' ); - - if( !button ){ - throw new Error( 'modeButton needs an options object or string name of a function' ); - } - - if( button && jQuery.type( options ) === 'string' ){ - var fnName = options; - if( button && jQuery.type( button[ fnName ] ) === 'function' ){ - return button[ fnName ].apply( button, jQuery.makeArray( arguments ).slice( 1 ) ); - } - } - return button; - } - }); -}()); diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 static/scripts/packed/jq-plugins/ui/mode-button.js --- /dev/null +++ b/static/scripts/packed/jq-plugins/ui/mode-button.js @@ -0,0 +1,1 @@ +(function(a){if(typeof define==="function"&&define.amd){define([],a)}else{a(jQuery)}}(function(){function c(o,n){this.currModeIndex=0;return this._init(o,n)}c.prototype.DATA_KEY="mode-button";c.prototype.defaults={switchModesOnClick:true};c.prototype._init=function j(o,n){n=n||{};this.$element=$(o);this.options=$.extend(true,{},this.defaults,n);if(!n.modes){throw new Error('ModeButton requires a "modes" array')}var q=this;this.$element.click(function p(r){q.callModeFn();if(q.options.switchModesOnClick){q._incModeIndex()}$(this).html(q.options.modes[q.currModeIndex].html)});return this.reset()};c.prototype._incModeIndex=function l(){this.currModeIndex+=1;if(this.currModeIndex>=this.options.modes.length){this.currModeIndex=0}return this};c.prototype._getModeIndex=function f(n){for(var o=0;o<this.options.modes.length;o+=1){if(this.options.modes[o].mode===n){return o}}throw new Error("mode not found: "+n)};c.prototype._setModeByIndex=function m(n){var o=this.options.modes[n];if(!o){throw new Error("mode index not found: "+n)}this.currModeIndex=n;if(o.html){this.$element.html(o.html)}return this};c.prototype.currentMode=function d(){return this.options.modes[this.currModeIndex]};c.prototype.current=function i(){return this.currentMode().mode};c.prototype.getMode=function g(n){if(!n){return this.currentMode()}return this.options.modes[(this._getModeIndex(n))]};c.prototype.hasMode=function b(n){try{return !!this.getMode(n)}catch(o){}return false};c.prototype.setMode=function a(n){return this._setModeByIndex(this._getModeIndex(n))};c.prototype.reset=function h(){this.currModeIndex=0;if(this.options.initialMode){this.currModeIndex=this._getModeIndex(this.options.initialMode)}return this._setModeByIndex(this.currModeIndex)};c.prototype.callModeFn=function e(n){var o=this.getMode(n).onclick;if(o&&$.type(o==="function")){return o.call(this.$element.get(0))}return undefined};$.fn.modeButton=function k(n){if(!this.size()){return this}if($.type(n)==="object"){return this.map(function(){var r=$(this);r.data("mode-button",new c(r,n));return this})}var p=$(this[0]),o=p.data("mode-button");if(!o){throw new Error("modeButton needs an options object or string name of a function")}if(o&&$.type(n)==="string"){var q=n;if(o&&$.type(o[q])==="function"){return o[q].apply(o,$.makeArray(arguments).slice(1))}}return o}})); \ No newline at end of file diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 static/scripts/packed/mvc/history/multi-panel.js --- a/static/scripts/packed/mvc/history/multi-panel.js +++ b/static/scripts/packed/mvc/history/multi-panel.js @@ -1,1 +1,1 @@ -define(["mvc/history/history-model","mvc/history/history-panel-edit","mvc/base-mvc","utils/ajax-queue"],function(d,l,z,a){window.HISTORY_MODEL=d;function g(H,E){E=E||{};if(!(Galaxy&&Galaxy.modal)){return H.copy()}var F=H.get("name"),C="Copy of '"+F+"'";function D(J){if(!J){if(!Galaxy.modal.$("#invalid-title").size()){var I=$("<p/>").attr("id","invalid-title").css({color:"red","margin-top":"8px"}).addClass("bg-danger").text(_l("Please enter a valid history title"));Galaxy.modal.$(".modal-body").append(I)}return false}return J}function G(I){var J=$('<p><span class="fa fa-spinner fa-spin"></span> Copying history...</p>').css("margin-top","8px");Galaxy.modal.$(".modal-body").append(J);H.copy(true,I).fail(function(){alert(_l("History could not be copied. Please contact a Galaxy administrator"))}).always(function(){Galaxy.modal.hide()})}Galaxy.modal.show(_.extend({title:_l("Copying history")+' "'+F+'"',body:$(['<label for="copy-modal-title">',_l("Enter a title for the copied history"),":","</label><br />",'<input id="copy-modal-title" class="form-control" style="width: 100%" value="',C,'" />'].join("")),buttons:{Cancel:function(){Galaxy.modal.hide()},Copy:function(){var I=Galaxy.modal.$("#copy-modal-title").val();if(!D(I)){return}G(I)}}},E));$("#copy-modal-title").focus().select()}var B=Backbone.View.extend(z.LoggableMixin).extend({tagName:"div",className:"history-column flex-column flex-row-container",id:function q(){if(!this.model){return""}return"history-column-"+this.model.get("id")},initialize:function c(C){C=C||{};this.panel=C.panel||this.createPanel(C);this.setUpListeners()},createPanel:function u(D){D=_.extend({model:this.model,dragItems:true},D);var C=new l.HistoryPanelEdit(D);C._renderEmptyMessage=this.__patch_renderEmptyMessage;return C},__patch_renderEmptyMessage:function(E){var D=this,F=_.chain(this.model.get("state_ids")).values().flatten().value().length,C=D.$emptyMessage(E);if(!_.isEmpty(D.hdaViews)){C.hide()}else{if(F&&!this.model.contents.length){C.empty().append($('<span class="fa fa-spinner fa-spin"></span><i>loading datasets...</i>')).show()}else{if(D.searchFor){C.text(D.noneFoundMsg).show()}else{C.text(D.emptyMsg).show()}}}return C},setUpListeners:function f(){var C=this;this.once("rendered",function(){C.trigger("rendered:initial",C)});this.setUpPanelListeners()},setUpPanelListeners:function k(){var C=this;this.listenTo(this.panel,{rendered:function(){C.trigger("rendered",C)}},this)},inView:function(C,D){var F=this.$el.offset().left,E=F+this.$el.width();if(E<C){return false}if(F>D){return false}return true},$panel:function e(){return this.$(".history-panel")},render:function A(D){D=(D!==undefined)?(D):("fast");var C=this.model?this.model.toJSON():{};this.$el.html(this.template(C));this.renderPanel(D);this.setUpBehaviors();return this},setUpBehaviors:function v(){},template:function w(D){D=D||{};var C=['<div class="panel-controls clear flex-row">',this.controlsLeftTemplate(),'<div class="pull-right">','<button class="delete-history btn btn-default">',D.deleted?_l("Undelete"):_l("Delete"),"</button>",'<button class="copy-history btn btn-default">',_l("Copy"),"</button>","</div>","</div>",'<div class="inner flex-row flex-column-container">','<div id="history-',D.id,'" class="history-column history-panel flex-column"></div>',"</div>"].join("");return $(C)},controlsLeftTemplate:function(){return(this.currentHistory)?['<div class="pull-left">','<button class="create-new btn btn-default">',_l("Create new"),"</button> ","</div>"].join(""):['<div class="pull-left">','<button class="switch-to btn btn-default">',_l("Switch to"),"</button>","</div>"].join("")},renderPanel:function h(C){C=(C!==undefined)?(C):("fast");this.panel.setElement(this.$panel()).render(C);return this},events:{"click .switch-to.btn":function(){this.model.setAsCurrent()},"click .delete-history.btn":function(){var C=this,D;if(this.model.get("deleted")){D=this.model.undelete()}else{D=this.model._delete()}D.fail(function(G,E,F){alert(_l("Could not delete the history")+":\n"+F)}).done(function(E){C.render()})},"click .copy-history.btn":"copy"},copy:function s(){g(this.model)},toString:function(){return"HistoryPanelColumn("+(this.panel?this.panel:"")+")"}});var m=Backbone.View.extend(z.LoggableMixin).extend({initialize:function c(C){C=C||{};this.log(this+".init",C);if(!C.currentHistoryId){throw new Error(this+" requires a currentHistoryId in the options")}this.currentHistoryId=C.currentHistoryId;this.options={columnWidth:312,borderWidth:1,columnGap:8,headerHeight:29,footerHeight:0,controlsHeight:20};this.order=C.order||"update";this.hdaQueue=new a.NamedAjaxQueue([],false);this.collection=null;this.setCollection(C.histories||[]);this.columnMap={};this.createColumns(C.columnOptions);this.setUpListeners()},setUpListeners:function f(){},setCollection:function y(D){var C=this;C.stopListening(C.collection);C.collection=D;C.sortCollection(C.order,{silent:true});C.setUpCollectionListeners();C.trigger("new-collection",C);return C},setUpCollectionListeners:function(){var C=this,D=C.collection;C.listenTo(D,{add:C.addAsCurrentColumn,"set-as-current":C.setCurrentHistory,"change:deleted":C.handleDeletedHistory,sort:function(){C.renderColumns(0)}})},setCurrentHistory:function p(D){var C=this.columnMap[this.currentHistoryId];if(C){C.currentHistory=false;C.$el.height("")}this.currentHistoryId=D.id;var E=this.columnMap[this.currentHistoryId];E.currentHistory=true;this.sortCollection();multipanel._recalcFirstColumnHeight();return E},handleDeletedHistory:function b(D){if(D.get("deleted")){this.log("handleDeletedHistory",this.collection.includeDeleted,D);var C=this;column=C.columnMap[D.id];if(!column){return}if(column.model.id===this.currentHistoryId){}else{if(!C.collection.includeDeleted){C.removeColumn(column)}}}},sortCollection:function(C,D){C=C||this.order;var E=this.currentHistoryId;switch(C){case"name":this.collection.comparator=function(F){return[F.id!==E,F.get("name").toLowerCase()]};break;case"size":this.collection.comparator=function(F){return[F.id!==E,F.get("size")]};break;default:this.collection.comparator=function(F){return[F.id!==E,Date(F.get("update_time"))]}}this.collection.sort(D);return this.collection},setOrder:function(C){if(["update","name","size"].indexOf(C)===-1){C="update"}this.order=C;this.sortCollection();return this},create:function(C){return this.collection.create({current:true})},createColumns:function r(D){D=D||{};var C=this;this.columnMap={};C.collection.each(function(E,F){var G=C.createColumn(E,D);C.columnMap[E.id]=G})},createColumn:function t(E,C){C=_.extend({},C,{model:E});var D=new B(C);if(E.id===this.currentHistoryId){D.currentHistory=true}this.setUpColumnListeners(D);return D},sortedFilteredColumns:function(C){C=C||this.filters;if(!C||!C.length){return this.sortedColumns()}var D=this;return D.sortedColumns().filter(function(G,F){var E=G.currentHistory||_.every(C.map(function(H){return H.call(G)}));return E})},sortedColumns:function(){var D=this;var C=this.collection.map(function(F,E){return D.columnMap[F.id]});return C},addColumn:function o(E,C){C=C!==undefined?C:true;var D=this.createColumn(E);this.columnMap[E.id]=D;if(C){this.renderColumns()}return D},addAsCurrentColumn:function o(E){var D=this,C=this.addColumn(E,false);this.setCurrentHistory(E);C.once("rendered",function(){D.queueHdaFetch(C)});return C},removeColumn:function x(E,D){D=D!==undefined?D:true;this.log("removeColumn",E);if(!E){return}var F=this,C=this.options.columnWidth+this.options.columnGap;E.$el.fadeOut("fast",function(){if(D){$(this).remove();F.$(".middle").width(F.$(".middle").width()-C);F.checkColumnsInView();F._recalcFirstColumnHeight()}F.stopListening(E.panel);F.stopListening(E);delete F.columnMap[E.model.id];E.remove()})},setUpColumnListeners:function n(C){var D=this;D.listenTo(C,{"in-view":D.queueHdaFetch});D.listenTo(C.panel,{"view:draggable:dragstart":function(H,F,E,G){D._dropData=JSON.parse(H.dataTransfer.getData("text"));D.currentColumnDropTargetOn()},"view:draggable:dragend":function(H,F,E,G){D._dropData=null;D.currentColumnDropTargetOff()},"droptarget:drop":function(G,H,F){var I=D._dropData.filter(function(J){return(_.isObject(J)&&J.id&&J.model_class==="HistoryDatasetAssociation")});D._dropData=null;var E=new a.NamedAjaxQueue();I.forEach(function(J){E.add({name:"copy-"+J.id,fn:function(){return F.model.contents.copy(J.id)}})});E.start();E.done(function(J){F.model.fetch()})}})},columnMapLength:function(){return Object.keys(this.columnMap).length},render:function A(D){D=D!==undefined?D:this.fxSpeed;var C=this;C.log(C+".render");C.$el.html(C.template(C.options));C.renderColumns(D);C.setUpBehaviors();C.trigger("rendered",C);return C},template:function w(C){C=C||{};var D=[];if(this.options.headerHeight){D=D.concat(['<div class="loading-overlay flex-row"><div class="loading-overlay-message">loading...</div></div>','<div class="header flex-column-container">','<div class="header-control header-control-left flex-column">','<button class="done btn btn-default">',_l("Done"),"</button>",'<button class="include-deleted btn btn-default"></button>','<div class="order btn-group">','<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">',_l("Order histories by")+'... <span class="caret"></span>',"</button>",'<ul class="dropdown-menu" role="menu">','<li><a href="javascript:void(0);" class="order-update">',_l("Time of last update"),"</a></li>",'<li><a href="javascript:void(0);" class="order-name">',_l("Name"),"</a></li>",'<li><a href="javascript:void(0);" class="order-size">',_l("Size"),"</a></li>","</ul>","</div>",'<div id="search-histories" class="header-search"></div>',"</div>",'<div class="header-control header-control-center flex-column">','<div class="header-info">',"</div>","</div>",'<div class="header-control header-control-right flex-column">','<div id="search-datasets" class="header-search"></div>','<button id="toggle-deleted" class="btn btn-default">',_l("Include deleted datasets"),"</button>",'<button id="toggle-hidden" class="btn btn-default">',_l("Include hidden datasets"),"</button>","</div>","</div>"])}D=D.concat(['<div class="outer-middle flex-row flex-row-container">','<div class="middle flex-column-container flex-row"></div>',"</div>",'<div class="footer flex-column-container">',"</div>"]);return $(D.join(""))},renderColumns:function j(F){F=F!==undefined?F:this.fxSpeed;var E=this,C=E.sortedFilteredColumns();E.$(".middle").width(C.length*(this.options.columnWidth+this.options.columnGap)+this.options.columnGap+16);var D=E.$(".middle");D.empty();C.forEach(function(H,G){H.$el.appendTo(D);H.delegateEvents();E.renderColumn(H,F)});if(this.searchFor&&C.length<=1){}else{E.checkColumnsInView();this._recalcFirstColumnHeight()}return C},renderColumn:function(C,D){D=D!==undefined?D:this.fxSpeed;return C.render(D)},queueHdaFetch:function i(E){if(E.model.contents.length===0&&!E.model.get("empty")){var C={},D=_.values(E.panel.storage.get("expandedIds")).join();if(D){C.dataset_details=D}this.hdaQueue.add({name:E.model.id,fn:function(){var F=E.model.contents.fetch({data:C,silent:true});return F.done(function(G){E.panel.renderItems()})}});if(!this.hdaQueue.running){this.hdaQueue.start()}}},queueHdaFetchDetails:function(C){if((C.model.contents.length===0&&!C.model.get("empty"))||(!C.model.contents.haveDetails())){this.hdaQueue.add({name:C.model.id,fn:function(){var D=C.model.contents.fetch({data:{details:"all"},silent:true});return D.done(function(E){C.panel.renderItems()})}});if(!this.hdaQueue.running){this.hdaQueue.start()}}},renderInfo:function(C){this.$(".header .header-info").text(C)},events:{"click .done.btn":function(){window.location="/"},"click .create-new.btn":"create","click .order .order-update":function(C){this.setOrder("update")},"click .order .order-name":function(C){this.setOrder("name")},"click .order .order-size":function(C){this.setOrder("size")}},includeDeletedHistories:function(){window.location+=(/\?/.test(window.location.toString()))?("&"):("?")+"include_deleted_histories=True"},excludeDeletedHistories:function(){window.location=window.location.toString().replace(/[&\?]include_deleted_histories=True/g,"")},setUpBehaviors:function(){var D=this;D.$(".include-deleted").modeButton({initialMode:this.collection.includeDeleted?"exclude":"include",switchModesOnClick:false,modes:[{mode:"include",html:_l("Include deleted histories"),onclick:_.bind(D.includeDeletedHistories,D)},{mode:"exclude",html:_l("Exclude deleted histories"),onclick:_.bind(D.excludeDeletedHistories,D)}]});D.$("#search-histories").searchInput({name:"search-histories",placeholder:_l("search histories"),onsearch:function(E){D.searchFor=E;D.filters=[function(){return this.model.matchesAll(D.searchFor)}];D.renderColumns(0)},onclear:function(E){D.searchFor=null;D.filters=[];D.renderColumns(0)}});D.$("#search-datasets").searchInput({name:"search-datasets",placeholder:_l("search all datasets"),onfirstsearch:function(E){D.hdaQueue.clear();D.$("#search-datasets").searchInput("toggle-loading");D.searchFor=E;D.sortedFilteredColumns().forEach(function(F){F.panel.searchItems(E);D.queueHdaFetchDetails(F)});D.hdaQueue.progress(function(F){D.renderInfo([_l("searching"),(F.curr+1),_l("of"),F.total].join(" "))});D.hdaQueue.deferred.done(function(){D.renderInfo("");D.$("#search-datasets").searchInput("toggle-loading")})},onsearch:function(E){D.searchFor=E;D.sortedFilteredColumns().forEach(function(F){F.panel.searchItems(E)})},onclear:function(E){D.searchFor=null;D.sortedFilteredColumns().forEach(function(F){F.panel.clearSearch()})}});D.$("#toggle-deleted").modeButton({initialMode:"include",modes:[{mode:"exclude",html:_l("Exclude deleted datasets")},{mode:"include",html:_l("Include deleted datasets")}]}).click(function(){var E=$(this).modeButton("getMode").mode==="exclude";D.sortedFilteredColumns().forEach(function(G,F){_.delay(function(){G.panel.toggleShowDeleted(E,false)},F*200)})});D.$("#toggle-hidden").modeButton({initialMode:"include",modes:[{mode:"exclude",html:_l("Exclude hidden datasets")},{mode:"include",html:_l("Include hidden datasets")}]}).click(function(){var E=$(this).modeButton("getMode").mode==="exclude";D.sortedFilteredColumns().forEach(function(G,F){_.delay(function(){G.panel.toggleShowHidden(E,false)},F*200)})});$(window).resize(function(){D._recalcFirstColumnHeight()});var C=_.debounce(_.bind(this.checkColumnsInView,this),100);this.$(".middle").parent().scroll(C)},_recalcFirstColumnHeight:function(){var C=this.$(".history-column").first(),E=this.$(".middle").height(),D=C.find(".panel-controls").height();C.height(E).find(".inner").height(E-D)},_viewport:function(){var C=this.$(".middle").parent().offset().left;return{left:C,right:C+this.$(".middle").parent().width()}},columnsInView:function(){var C=this._viewport();return this.sortedFilteredColumns().filter(function(D){return D.currentHistory||D.inView(C.left,C.right)})},checkColumnsInView:function(){this.columnsInView().forEach(function(C){C.trigger("in-view",C)})},currentColumnDropTargetOn:function(){var C=this.columnMap[this.currentHistoryId];if(!C){return}C.panel.dataDropped=function(D){};C.panel.dropTargetOn()},currentColumnDropTargetOff:function(){var C=this.columnMap[this.currentHistoryId];if(!C){return}C.panel.dataDropped=l.HistoryPanelEdit.prototype.dataDrop;C.panel.dropTargetOff()},toString:function(){return"MultiPanelColumns("+(this.columns?this.columns.length:0)+")"}});return{MultiPanelColumns:m}}); \ No newline at end of file +define(["mvc/history/history-model","mvc/history/history-panel-edit","mvc/base-mvc","utils/ajax-queue","jq-plugins/ui/mode-button"],function(d,l,z,a){window.HISTORY_MODEL=d;function g(H,E){E=E||{};if(!(Galaxy&&Galaxy.modal)){return H.copy()}var F=H.get("name"),C="Copy of '"+F+"'";function D(J){if(!J){if(!Galaxy.modal.$("#invalid-title").size()){var I=$("<p/>").attr("id","invalid-title").css({color:"red","margin-top":"8px"}).addClass("bg-danger").text(_l("Please enter a valid history title"));Galaxy.modal.$(".modal-body").append(I)}return false}return J}function G(I){var J=$('<p><span class="fa fa-spinner fa-spin"></span> Copying history...</p>').css("margin-top","8px");Galaxy.modal.$(".modal-body").append(J);H.copy(true,I).fail(function(){alert(_l("History could not be copied. Please contact a Galaxy administrator"))}).always(function(){Galaxy.modal.hide()})}Galaxy.modal.show(_.extend({title:_l("Copying history")+' "'+F+'"',body:$(['<label for="copy-modal-title">',_l("Enter a title for the copied history"),":","</label><br />",'<input id="copy-modal-title" class="form-control" style="width: 100%" value="',C,'" />'].join("")),buttons:{Cancel:function(){Galaxy.modal.hide()},Copy:function(){var I=Galaxy.modal.$("#copy-modal-title").val();if(!D(I)){return}G(I)}}},E));$("#copy-modal-title").focus().select()}var B=Backbone.View.extend(z.LoggableMixin).extend({tagName:"div",className:"history-column flex-column flex-row-container",id:function q(){if(!this.model){return""}return"history-column-"+this.model.get("id")},initialize:function c(C){C=C||{};this.panel=C.panel||this.createPanel(C);this.setUpListeners()},createPanel:function u(D){D=_.extend({model:this.model,dragItems:true},D);var C=new l.HistoryPanelEdit(D);C._renderEmptyMessage=this.__patch_renderEmptyMessage;return C},__patch_renderEmptyMessage:function(E){var D=this,F=_.chain(this.model.get("state_ids")).values().flatten().value().length,C=D.$emptyMessage(E);if(!_.isEmpty(D.hdaViews)){C.hide()}else{if(F&&!this.model.contents.length){C.empty().append($('<span class="fa fa-spinner fa-spin"></span><i>loading datasets...</i>')).show()}else{if(D.searchFor){C.text(D.noneFoundMsg).show()}else{C.text(D.emptyMsg).show()}}}return C},setUpListeners:function f(){var C=this;this.once("rendered",function(){C.trigger("rendered:initial",C)});this.setUpPanelListeners()},setUpPanelListeners:function k(){var C=this;this.listenTo(this.panel,{rendered:function(){C.trigger("rendered",C)}},this)},inView:function(C,D){var F=this.$el.offset().left,E=F+this.$el.width();if(E<C){return false}if(F>D){return false}return true},$panel:function e(){return this.$(".history-panel")},render:function A(D){D=(D!==undefined)?(D):("fast");var C=this.model?this.model.toJSON():{};this.$el.html(this.template(C));this.renderPanel(D);this.setUpBehaviors();return this},setUpBehaviors:function v(){},template:function w(D){D=D||{};var C=['<div class="panel-controls clear flex-row">',this.controlsLeftTemplate(),'<div class="pull-right">','<button class="delete-history btn btn-default">',D.deleted?_l("Undelete"):_l("Delete"),"</button>",'<button class="copy-history btn btn-default">',_l("Copy"),"</button>","</div>","</div>",'<div class="inner flex-row flex-column-container">','<div id="history-',D.id,'" class="history-column history-panel flex-column"></div>',"</div>"].join("");return $(C)},controlsLeftTemplate:function(){return(this.currentHistory)?['<div class="pull-left">','<button class="create-new btn btn-default">',_l("Create new"),"</button> ","</div>"].join(""):['<div class="pull-left">','<button class="switch-to btn btn-default">',_l("Switch to"),"</button>","</div>"].join("")},renderPanel:function h(C){C=(C!==undefined)?(C):("fast");this.panel.setElement(this.$panel()).render(C);return this},events:{"click .switch-to.btn":function(){this.model.setAsCurrent()},"click .delete-history.btn":function(){var C=this,D;if(this.model.get("deleted")){D=this.model.undelete()}else{D=this.model._delete()}D.fail(function(G,E,F){alert(_l("Could not delete the history")+":\n"+F)}).done(function(E){C.render()})},"click .copy-history.btn":"copy"},copy:function s(){g(this.model)},toString:function(){return"HistoryPanelColumn("+(this.panel?this.panel:"")+")"}});var m=Backbone.View.extend(z.LoggableMixin).extend({initialize:function c(C){C=C||{};this.log(this+".init",C);if(!C.currentHistoryId){throw new Error(this+" requires a currentHistoryId in the options")}this.currentHistoryId=C.currentHistoryId;this.options={columnWidth:312,borderWidth:1,columnGap:8,headerHeight:29,footerHeight:0,controlsHeight:20};this.order=C.order||"update";this.hdaQueue=new a.NamedAjaxQueue([],false);this.collection=null;this.setCollection(C.histories||[]);this.columnMap={};this.createColumns(C.columnOptions);this.setUpListeners()},setUpListeners:function f(){},setCollection:function y(D){var C=this;C.stopListening(C.collection);C.collection=D;C.sortCollection(C.order,{silent:true});C.setUpCollectionListeners();C.trigger("new-collection",C);return C},setUpCollectionListeners:function(){var C=this,D=C.collection;C.listenTo(D,{add:C.addAsCurrentColumn,"set-as-current":C.setCurrentHistory,"change:deleted":C.handleDeletedHistory,sort:function(){C.renderColumns(0)}})},setCurrentHistory:function p(D){var C=this.columnMap[this.currentHistoryId];if(C){C.currentHistory=false;C.$el.height("")}this.currentHistoryId=D.id;var E=this.columnMap[this.currentHistoryId];E.currentHistory=true;this.sortCollection();multipanel._recalcFirstColumnHeight();return E},handleDeletedHistory:function b(D){if(D.get("deleted")){this.log("handleDeletedHistory",this.collection.includeDeleted,D);var C=this;column=C.columnMap[D.id];if(!column){return}if(column.model.id===this.currentHistoryId){}else{if(!C.collection.includeDeleted){C.removeColumn(column)}}}},sortCollection:function(C,D){C=C||this.order;var E=this.currentHistoryId;switch(C){case"name":this.collection.comparator=function(F){return[F.id!==E,F.get("name").toLowerCase()]};break;case"size":this.collection.comparator=function(F){return[F.id!==E,F.get("size")]};break;default:this.collection.comparator=function(F){return[F.id!==E,Date(F.get("update_time"))]}}this.collection.sort(D);return this.collection},setOrder:function(C){if(["update","name","size"].indexOf(C)===-1){C="update"}this.order=C;this.sortCollection();return this},create:function(C){return this.collection.create({current:true})},createColumns:function r(D){D=D||{};var C=this;this.columnMap={};C.collection.each(function(E,F){var G=C.createColumn(E,D);C.columnMap[E.id]=G})},createColumn:function t(E,C){C=_.extend({},C,{model:E});var D=new B(C);if(E.id===this.currentHistoryId){D.currentHistory=true}this.setUpColumnListeners(D);return D},sortedFilteredColumns:function(C){C=C||this.filters;if(!C||!C.length){return this.sortedColumns()}var D=this;return D.sortedColumns().filter(function(G,F){var E=G.currentHistory||_.every(C.map(function(H){return H.call(G)}));return E})},sortedColumns:function(){var D=this;var C=this.collection.map(function(F,E){return D.columnMap[F.id]});return C},addColumn:function o(E,C){C=C!==undefined?C:true;var D=this.createColumn(E);this.columnMap[E.id]=D;if(C){this.renderColumns()}return D},addAsCurrentColumn:function o(E){var D=this,C=this.addColumn(E,false);this.setCurrentHistory(E);C.once("rendered",function(){D.queueHdaFetch(C)});return C},removeColumn:function x(E,D){D=D!==undefined?D:true;this.log("removeColumn",E);if(!E){return}var F=this,C=this.options.columnWidth+this.options.columnGap;E.$el.fadeOut("fast",function(){if(D){$(this).remove();F.$(".middle").width(F.$(".middle").width()-C);F.checkColumnsInView();F._recalcFirstColumnHeight()}F.stopListening(E.panel);F.stopListening(E);delete F.columnMap[E.model.id];E.remove()})},setUpColumnListeners:function n(C){var D=this;D.listenTo(C,{"in-view":D.queueHdaFetch});D.listenTo(C.panel,{"view:draggable:dragstart":function(H,F,E,G){D._dropData=JSON.parse(H.dataTransfer.getData("text"));D.currentColumnDropTargetOn()},"view:draggable:dragend":function(H,F,E,G){D._dropData=null;D.currentColumnDropTargetOff()},"droptarget:drop":function(G,H,F){var I=D._dropData.filter(function(J){return(_.isObject(J)&&J.id&&J.model_class==="HistoryDatasetAssociation")});D._dropData=null;var E=new a.NamedAjaxQueue();I.forEach(function(J){E.add({name:"copy-"+J.id,fn:function(){return F.model.contents.copy(J.id)}})});E.start();E.done(function(J){F.model.fetch()})}})},columnMapLength:function(){return Object.keys(this.columnMap).length},render:function A(D){D=D!==undefined?D:this.fxSpeed;var C=this;C.log(C+".render");C.$el.html(C.template(C.options));C.renderColumns(D);C.setUpBehaviors();C.trigger("rendered",C);return C},template:function w(C){C=C||{};var D=[];if(this.options.headerHeight){D=D.concat(['<div class="loading-overlay flex-row"><div class="loading-overlay-message">loading...</div></div>','<div class="header flex-column-container">','<div class="header-control header-control-left flex-column">','<button class="done btn btn-default">',_l("Done"),"</button>",'<button class="include-deleted btn btn-default"></button>','<div class="order btn-group">','<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">',_l("Order histories by")+'... <span class="caret"></span>',"</button>",'<ul class="dropdown-menu" role="menu">','<li><a href="javascript:void(0);" class="order-update">',_l("Time of last update"),"</a></li>",'<li><a href="javascript:void(0);" class="order-name">',_l("Name"),"</a></li>",'<li><a href="javascript:void(0);" class="order-size">',_l("Size"),"</a></li>","</ul>","</div>",'<div id="search-histories" class="header-search"></div>',"</div>",'<div class="header-control header-control-center flex-column">','<div class="header-info">',"</div>","</div>",'<div class="header-control header-control-right flex-column">','<div id="search-datasets" class="header-search"></div>','<button id="toggle-deleted" class="btn btn-default">',_l("Include deleted datasets"),"</button>",'<button id="toggle-hidden" class="btn btn-default">',_l("Include hidden datasets"),"</button>","</div>","</div>"])}D=D.concat(['<div class="outer-middle flex-row flex-row-container">','<div class="middle flex-column-container flex-row"></div>',"</div>",'<div class="footer flex-column-container">',"</div>"]);return $(D.join(""))},renderColumns:function j(F){F=F!==undefined?F:this.fxSpeed;var E=this,C=E.sortedFilteredColumns();E.$(".middle").width(C.length*(this.options.columnWidth+this.options.columnGap)+this.options.columnGap+16);var D=E.$(".middle");D.empty();C.forEach(function(H,G){H.$el.appendTo(D);H.delegateEvents();E.renderColumn(H,F)});if(this.searchFor&&C.length<=1){}else{E.checkColumnsInView();this._recalcFirstColumnHeight()}return C},renderColumn:function(C,D){D=D!==undefined?D:this.fxSpeed;return C.render(D)},queueHdaFetch:function i(E){if(E.model.contents.length===0&&!E.model.get("empty")){var C={},D=_.values(E.panel.storage.get("expandedIds")).join();if(D){C.dataset_details=D}this.hdaQueue.add({name:E.model.id,fn:function(){var F=E.model.contents.fetch({data:C,silent:true});return F.done(function(G){E.panel.renderItems()})}});if(!this.hdaQueue.running){this.hdaQueue.start()}}},queueHdaFetchDetails:function(C){if((C.model.contents.length===0&&!C.model.get("empty"))||(!C.model.contents.haveDetails())){this.hdaQueue.add({name:C.model.id,fn:function(){var D=C.model.contents.fetch({data:{details:"all"},silent:true});return D.done(function(E){C.panel.renderItems()})}});if(!this.hdaQueue.running){this.hdaQueue.start()}}},renderInfo:function(C){this.$(".header .header-info").text(C)},events:{"click .done.btn":function(){window.location="/"},"click .create-new.btn":"create","click .order .order-update":function(C){this.setOrder("update")},"click .order .order-name":function(C){this.setOrder("name")},"click .order .order-size":function(C){this.setOrder("size")}},includeDeletedHistories:function(){window.location+=(/\?/.test(window.location.toString()))?("&"):("?")+"include_deleted_histories=True"},excludeDeletedHistories:function(){window.location=window.location.toString().replace(/[&\?]include_deleted_histories=True/g,"")},setUpBehaviors:function(){var D=this;D.$(".include-deleted").modeButton({initialMode:this.collection.includeDeleted?"exclude":"include",switchModesOnClick:false,modes:[{mode:"include",html:_l("Include deleted histories"),onclick:_.bind(D.includeDeletedHistories,D)},{mode:"exclude",html:_l("Exclude deleted histories"),onclick:_.bind(D.excludeDeletedHistories,D)}]});D.$("#search-histories").searchInput({name:"search-histories",placeholder:_l("search histories"),onsearch:function(E){D.searchFor=E;D.filters=[function(){return this.model.matchesAll(D.searchFor)}];D.renderColumns(0)},onclear:function(E){D.searchFor=null;D.filters=[];D.renderColumns(0)}});D.$("#search-datasets").searchInput({name:"search-datasets",placeholder:_l("search all datasets"),onfirstsearch:function(E){D.hdaQueue.clear();D.$("#search-datasets").searchInput("toggle-loading");D.searchFor=E;D.sortedFilteredColumns().forEach(function(F){F.panel.searchItems(E);D.queueHdaFetchDetails(F)});D.hdaQueue.progress(function(F){D.renderInfo([_l("searching"),(F.curr+1),_l("of"),F.total].join(" "))});D.hdaQueue.deferred.done(function(){D.renderInfo("");D.$("#search-datasets").searchInput("toggle-loading")})},onsearch:function(E){D.searchFor=E;D.sortedFilteredColumns().forEach(function(F){F.panel.searchItems(E)})},onclear:function(E){D.searchFor=null;D.sortedFilteredColumns().forEach(function(F){F.panel.clearSearch()})}});D.$("#toggle-deleted").modeButton({initialMode:"include",modes:[{mode:"exclude",html:_l("Exclude deleted datasets")},{mode:"include",html:_l("Include deleted datasets")}]}).click(function(){var E=$(this).modeButton("getMode").mode==="exclude";D.sortedFilteredColumns().forEach(function(G,F){_.delay(function(){G.panel.toggleShowDeleted(E,false)},F*200)})});D.$("#toggle-hidden").modeButton({initialMode:"include",modes:[{mode:"exclude",html:_l("Exclude hidden datasets")},{mode:"include",html:_l("Include hidden datasets")}]}).click(function(){var E=$(this).modeButton("getMode").mode==="exclude";D.sortedFilteredColumns().forEach(function(G,F){_.delay(function(){G.panel.toggleShowHidden(E,false)},F*200)})});$(window).resize(function(){D._recalcFirstColumnHeight()});var C=_.debounce(_.bind(this.checkColumnsInView,this),100);this.$(".middle").parent().scroll(C)},_recalcFirstColumnHeight:function(){var C=this.$(".history-column").first(),E=this.$(".middle").height(),D=C.find(".panel-controls").height();C.height(E).find(".inner").height(E-D)},_viewport:function(){var C=this.$(".middle").parent().offset().left;return{left:C,right:C+this.$(".middle").parent().width()}},columnsInView:function(){var C=this._viewport();return this.sortedFilteredColumns().filter(function(D){return D.currentHistory||D.inView(C.left,C.right)})},checkColumnsInView:function(){this.columnsInView().forEach(function(C){C.trigger("in-view",C)})},currentColumnDropTargetOn:function(){var C=this.columnMap[this.currentHistoryId];if(!C){return}C.panel.dataDropped=function(D){};C.panel.dropTargetOn()},currentColumnDropTargetOff:function(){var C=this.columnMap[this.currentHistoryId];if(!C){return}C.panel.dataDropped=l.HistoryPanelEdit.prototype.dataDrop;C.panel.dropTargetOff()},toString:function(){return"MultiPanelColumns("+(this.columns?this.columns.length:0)+")"}});return{MultiPanelColumns:m}}); \ No newline at end of file diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 static/scripts/packed/mvc/ui.js --- a/static/scripts/packed/mvc/ui.js +++ b/static/scripts/packed/mvc/ui.js @@ -1,1 +1,1 @@ -var IconButton=Backbone.Model.extend({defaults:{title:"",icon_class:"",on_click:null,menu_options:null,is_menu_button:true,id:null,href:null,target:null,enabled:true,visible:true,tooltip_config:{}}});var IconButtonView=Backbone.View.extend({initialize:function(){this.model.attributes.tooltip_config={placement:"bottom"};this.model.bind("change",this.render,this)},render:function(){this.$el.tooltip("hide");var a=this.template(this.model.toJSON());a.tooltip(this.model.get("tooltip_config"));this.$el.replaceWith(a);this.setElement(a);return this},events:{click:"click"},click:function(a){if(_.isFunction(this.model.get("on_click"))){this.model.get("on_click")(a);return false}return true},template:function(b){var a='title="'+b.title+'" class="icon-button';if(b.is_menu_button){a+=" menu-button"}a+=" "+b.icon_class;if(!b.enabled){a+="_disabled"}a+='"';if(b.id){a+=' id="'+b.id+'"'}a+=' href="'+b.href+'"';if(b.target){a+=' target="'+b.target+'"'}if(!b.visible){a+=' style="display: none;"'}if(b.enabled){a="<a "+a+"/>"}else{a="<span "+a+"/>"}return $(a)}});var IconButtonCollection=Backbone.Collection.extend({model:IconButton});var IconButtonMenuView=Backbone.View.extend({tagName:"div",initialize:function(){this.render()},render:function(){var a=this;this.collection.each(function(d){var b=$("<a/>").attr("href","javascript:void(0)").attr("title",d.attributes.title).addClass("icon-button menu-button").addClass(d.attributes.icon_class).appendTo(a.$el).click(d.attributes.on_click);if(d.attributes.tooltip_config){b.tooltip(d.attributes.tooltip_config)}var c=d.get("options");if(c){make_popupmenu(b,c)}});return this}});var create_icon_buttons_menu=function(b,a){if(!a){a={}}var c=new IconButtonCollection(_.map(b,function(d){return new IconButton(_.extend(d,a))}));return new IconButtonMenuView({collection:c})};var Grid=Backbone.Collection.extend({});var GridView=Backbone.View.extend({});var PopupMenu=Backbone.View.extend({initialize:function(b,a){this.$button=b;if(!this.$button.size()){this.$button=$("<div/>")}this.options=a||[];var c=this;this.$button.click(function(d){$(".popmenu-wrapper").remove();c._renderAndShow(d);return false})},_renderAndShow:function(a){this.render();this.$el.appendTo("body").css(this._getShownPosition(a)).show();this._setUpCloseBehavior()},render:function(){this.$el.addClass("popmenu-wrapper").hide().css({position:"absolute"}).html(this.template(this.$button.attr("id"),this.options));if(this.options.length){var a=this;this.$el.find("li").each(function(c,b){var d=a.options[c];if(d.func){$(this).children("a.popupmenu-option").click(function(e){d.func.call(a,e,d)})}})}return this},template:function(b,a){return['<ul id="',b,'-menu" class="dropdown-menu">',this._templateOptions(a),"</ul>"].join("")},_templateOptions:function(a){if(!a.length){return"<li>(no options)</li>"}return _.map(a,function(d){if(d.divider){return'<li class="divider"></li>'}else{if(d.header){return['<li class="head"><a href="javascript:void(0);">',d.html,"</a></li>"].join("")}}var c=d.href||"javascript:void(0);",e=(d.target)?(' target="'+d.target+'"'):(""),b=(d.checked)?('<span class="fa fa-check"></span>'):("");return['<li><a class="popupmenu-option" href="',c,'"',e,">",b,d.html,"</a></li>"].join("")}).join("")},_getShownPosition:function(b){var c=this.$el.width();var a=b.pageX-c/2;a=Math.min(a,$(document).scrollLeft()+$(window).width()-c-5);a=Math.max(a,$(document).scrollLeft()+5);return{top:b.pageY,left:a}},_setUpCloseBehavior:function(){var c=this;function a(e){$(document).off("click.close_popup");if(window.parent!==window){try{$(window.parent.document).off("click.close_popup")}catch(d){}}else{try{$("iframe#galaxy_main").contents().off("click.close_popup")}catch(d){}}c.remove()}$("html").one("click.close_popup",a);if(window.parent!==window){try{$(window.parent.document).find("html").one("click.close_popup",a)}catch(b){}}else{try{$("iframe#galaxy_main").contents().one("click.close_popup",a)}catch(b){}}},addItem:function(b,a){a=(a>=0)?a:this.options.length;this.options.splice(a,0,b);return this},removeItem:function(a){if(a>=0){this.options.splice(a,1)}return this},findIndexByHtml:function(b){for(var a=0;a<this.options.length;a++){if(_.has(this.options[a],"html")&&(this.options[a].html===b)){return a}}return null},findItemByHtml:function(a){return this.options[(this.findIndexByHtml(a))]},toString:function(){return"PopupMenu"}});PopupMenu.create=function _create(b,a){return new PopupMenu(b,a)};PopupMenu.make_popupmenu=function(b,c){var a=[];_.each(c,function(f,d){var e={html:d};if(f===null){e.header=true}else{if(jQuery.type(f)==="function"){e.func=f}}a.push(e)});return new PopupMenu($(b),a)};PopupMenu.convertLinksToOptions=function(c,a){c=$(c);a=a||"a";var b=[];c.find(a).each(function(g,e){var f={},d=$(g);f.html=d.text();if(d.attr("href")){var j=d.attr("href"),k=d.attr("target"),h=d.attr("confirm");f.func=function(){if((h)&&(!confirm(h))){return}switch(k){case"_parent":window.parent.location=j;break;case"_top":window.top.location=j;break;default:window.location=j}}}b.push(f)});return b};PopupMenu.fromExistingDom=function(d,c,a){d=$(d);c=$(c);var b=PopupMenu.convertLinksToOptions(c,a);c.remove();return new PopupMenu(d,b)};PopupMenu.make_popup_menus=function(c,b,d){c=c||document;b=b||"div[popupmenu]";d=d||function(e,f){return"#"+e.attr("popupmenu")};var a=[];$(c).find(b).each(function(){var e=$(this),f=$(c).find(d(e,c));a.push(PopupMenu.fromDom(f,e));f.addClass("popup")});return a};var faIconButton=function(a){a=a||{};a.tooltipConfig=a.tooltipConfig||{placement:"bottom"};a.classes=["icon-btn"].concat(a.classes||[]);if(a.disabled){a.classes.push("disabled")}var b=['<a class="',a.classes.join(" "),'"',((a.title)?(' title="'+a.title+'"'):("")),((!a.disabled&&a.target)?(' target="'+a.target+'"'):("")),' href="',((!a.disabled&&a.href)?(a.href):("javascript:void(0);")),'">','<span class="fa ',a.faIcon,'"></span>',"</a>"].join("");var c=$(b).tooltip(a.tooltipConfig);if(_.isFunction(a.onclick)){c.click(a.onclick)}return c};function LoadingIndicator(a,c){var b=this;c=jQuery.extend({cover:false},c||{});function d(){var e=['<div class="loading-indicator">','<div class="loading-indicator-text">','<span class="fa fa-spinner fa-spin fa-lg"></span>','<span class="loading-indicator-message">loading...</span>',"</div>","</div>"].join("\n");var g=$(e).hide().css(c.css||{position:"fixed"}),f=g.children(".loading-indicator-text");if(c.cover){g.css({"z-index":2,top:a.css("top"),bottom:a.css("bottom"),left:a.css("left"),right:a.css("right"),opacity:0.5,"background-color":"white","text-align":"center"});f=g.children(".loading-indicator-text").css({"margin-top":"20px"})}else{f=g.children(".loading-indicator-text").css({margin:"12px 0px 0px 10px",opacity:"0.85",color:"grey"});f.children(".loading-indicator-message").css({margin:"0px 8px 0px 0px","font-style":"italic"})}return g}b.show=function(f,e,g){f=f||"loading...";e=e||"fast";a.parent().find(".loading-indicator").remove();b.$indicator=d().insertBefore(a);b.message(f);b.$indicator.fadeIn(e,g);return b};b.message=function(e){b.$indicator.find("i").text(e)};b.hide=function(e,f){e=e||"fast";if(b.$indicator&&b.$indicator.size()){b.$indicator.fadeOut(e,function(){b.$indicator.remove();if(f){f()}})}else{if(f){f()}}return b};return b}(function(){var b=window._l||function(d){return d};function a(k,q){var e=27,n=13,d=$(k),f=true,h={initialVal:"",name:"search",placeholder:"search",classes:"",onclear:function(){},onfirstsearch:null,onsearch:function(r){},minSearchLen:0,escWillClear:true,oninit:function(){}};function j(r){var s=$(this).parent().children("input");s.focus().val("").trigger("clear:searchInput");q.onclear()}function p(s,r){$(this).trigger("search:searchInput",r);if(typeof q.onfirstsearch==="function"&&f){f=false;q.onfirstsearch(r)}else{q.onsearch(r)}}function g(){return['<input type="text" name="',q.name,'" placeholder="',q.placeholder,'" ','class="search-query ',q.classes,'" ',"/>"].join("")}function m(){return $(g()).focus(function(r){$(this).select()}).keyup(function(s){s.preventDefault();s.stopPropagation();if(!$(this).val()){$(this).blur()}if(s.which===e&&q.escWillClear){j.call(this,s)}else{var r=$(this).val();if((s.which===n)||(q.minSearchLen&&r.length>=q.minSearchLen)){p.call(this,s,r)}else{if(!r.length){j.call(this,s)}}}}).on("change",function(r){p.call(this,r,$(this).val())}).val(q.initialVal)}function l(){return $(['<span class="search-clear fa fa-times-circle" ','title="',b("clear search (esc)"),'"></span>'].join("")).tooltip({placement:"bottom"}).click(function(r){j.call(this,r)})}function o(){return $(['<span class="search-loading fa fa-spinner fa-spin" ','title="',b("loading..."),'"></span>'].join("")).hide().tooltip({placement:"bottom"})}function i(){d.find(".search-loading").toggle();d.find(".search-clear").toggle()}if(jQuery.type(q)==="string"){if(q==="toggle-loading"){i()}return d}if(jQuery.type(q)==="object"){q=jQuery.extend(true,{},h,q)}return d.addClass("search-input").prepend([m(),l(),o()])}jQuery.fn.extend({searchInput:function c(d){return this.each(function(){return a(this,d)})}})}());(function(){function c(o,n){this.currModeIndex=0;return this._init(o,n)}c.prototype.DATA_KEY="mode-button";c.prototype.defaults={switchModesOnClick:true};c.prototype._init=function j(o,n){n=n||{};this.$element=$(o);this.options=jQuery.extend(true,{},this.defaults,n);if(!n.modes){throw new Error('ModeButton requires a "modes" array')}var q=this;this.$element.click(function p(r){q.callModeFn();if(q.options.switchModesOnClick){q._incModeIndex()}$(this).html(q.options.modes[q.currModeIndex].html)});return this.reset()};c.prototype._incModeIndex=function l(){this.currModeIndex+=1;if(this.currModeIndex>=this.options.modes.length){this.currModeIndex=0}return this};c.prototype._getModeIndex=function f(n){for(var o=0;o<this.options.modes.length;o+=1){if(this.options.modes[o].mode===n){return o}}throw new Error("mode not found: "+n)};c.prototype._setModeByIndex=function m(n){var o=this.options.modes[n];if(!o){throw new Error("mode index not found: "+n)}this.currModeIndex=n;if(o.html){this.$element.html(o.html)}return this};c.prototype.currentMode=function d(){return this.options.modes[this.currModeIndex]};c.prototype.current=function i(){return this.currentMode().mode};c.prototype.getMode=function g(n){if(!n){return this.currentMode()}return this.options.modes[(this._getModeIndex(n))]};c.prototype.hasMode=function b(n){try{return !!this.getMode(n)}catch(o){}return false};c.prototype.setMode=function a(n){return this._setModeByIndex(this._getModeIndex(n))};c.prototype.reset=function h(){this.currModeIndex=0;if(this.options.initialMode){this.currModeIndex=this._getModeIndex(this.options.initialMode)}return this._setModeByIndex(this.currModeIndex)};c.prototype.callModeFn=function e(n){var o=this.getMode(n).onclick;if(o&&jQuery.type(o==="function")){return o.call(this.$element.get(0))}return undefined};jQuery.fn.extend({modeButton:function k(n){if(!this.size()){return this}if(jQuery.type(n)==="object"){return this.map(function(){var r=$(this);r.data("mode-button",new c(r,n));return this})}var p=$(this[0]),o=p.data("mode-button");if(!o){throw new Error("modeButton needs an options object or string name of a function")}if(o&&jQuery.type(n)==="string"){var q=n;if(o&&jQuery.type(o[q])==="function"){return o[q].apply(o,jQuery.makeArray(arguments).slice(1))}}return o}})}()); \ No newline at end of file +var IconButton=Backbone.Model.extend({defaults:{title:"",icon_class:"",on_click:null,menu_options:null,is_menu_button:true,id:null,href:null,target:null,enabled:true,visible:true,tooltip_config:{}}});var IconButtonView=Backbone.View.extend({initialize:function(){this.model.attributes.tooltip_config={placement:"bottom"};this.model.bind("change",this.render,this)},render:function(){this.$el.tooltip("hide");var a=this.template(this.model.toJSON());a.tooltip(this.model.get("tooltip_config"));this.$el.replaceWith(a);this.setElement(a);return this},events:{click:"click"},click:function(a){if(_.isFunction(this.model.get("on_click"))){this.model.get("on_click")(a);return false}return true},template:function(b){var a='title="'+b.title+'" class="icon-button';if(b.is_menu_button){a+=" menu-button"}a+=" "+b.icon_class;if(!b.enabled){a+="_disabled"}a+='"';if(b.id){a+=' id="'+b.id+'"'}a+=' href="'+b.href+'"';if(b.target){a+=' target="'+b.target+'"'}if(!b.visible){a+=' style="display: none;"'}if(b.enabled){a="<a "+a+"/>"}else{a="<span "+a+"/>"}return $(a)}});var IconButtonCollection=Backbone.Collection.extend({model:IconButton});var IconButtonMenuView=Backbone.View.extend({tagName:"div",initialize:function(){this.render()},render:function(){var a=this;this.collection.each(function(d){var b=$("<a/>").attr("href","javascript:void(0)").attr("title",d.attributes.title).addClass("icon-button menu-button").addClass(d.attributes.icon_class).appendTo(a.$el).click(d.attributes.on_click);if(d.attributes.tooltip_config){b.tooltip(d.attributes.tooltip_config)}var c=d.get("options");if(c){make_popupmenu(b,c)}});return this}});var create_icon_buttons_menu=function(b,a){if(!a){a={}}var c=new IconButtonCollection(_.map(b,function(d){return new IconButton(_.extend(d,a))}));return new IconButtonMenuView({collection:c})};var Grid=Backbone.Collection.extend({});var GridView=Backbone.View.extend({});var PopupMenu=Backbone.View.extend({initialize:function(b,a){this.$button=b;if(!this.$button.size()){this.$button=$("<div/>")}this.options=a||[];var c=this;this.$button.click(function(d){$(".popmenu-wrapper").remove();c._renderAndShow(d);return false})},_renderAndShow:function(a){this.render();this.$el.appendTo("body").css(this._getShownPosition(a)).show();this._setUpCloseBehavior()},render:function(){this.$el.addClass("popmenu-wrapper").hide().css({position:"absolute"}).html(this.template(this.$button.attr("id"),this.options));if(this.options.length){var a=this;this.$el.find("li").each(function(c,b){var d=a.options[c];if(d.func){$(this).children("a.popupmenu-option").click(function(e){d.func.call(a,e,d)})}})}return this},template:function(b,a){return['<ul id="',b,'-menu" class="dropdown-menu">',this._templateOptions(a),"</ul>"].join("")},_templateOptions:function(a){if(!a.length){return"<li>(no options)</li>"}return _.map(a,function(d){if(d.divider){return'<li class="divider"></li>'}else{if(d.header){return['<li class="head"><a href="javascript:void(0);">',d.html,"</a></li>"].join("")}}var c=d.href||"javascript:void(0);",e=(d.target)?(' target="'+d.target+'"'):(""),b=(d.checked)?('<span class="fa fa-check"></span>'):("");return['<li><a class="popupmenu-option" href="',c,'"',e,">",b,d.html,"</a></li>"].join("")}).join("")},_getShownPosition:function(b){var c=this.$el.width();var a=b.pageX-c/2;a=Math.min(a,$(document).scrollLeft()+$(window).width()-c-5);a=Math.max(a,$(document).scrollLeft()+5);return{top:b.pageY,left:a}},_setUpCloseBehavior:function(){var c=this;function a(e){$(document).off("click.close_popup");if(window.parent!==window){try{$(window.parent.document).off("click.close_popup")}catch(d){}}else{try{$("iframe#galaxy_main").contents().off("click.close_popup")}catch(d){}}c.remove()}$("html").one("click.close_popup",a);if(window.parent!==window){try{$(window.parent.document).find("html").one("click.close_popup",a)}catch(b){}}else{try{$("iframe#galaxy_main").contents().one("click.close_popup",a)}catch(b){}}},addItem:function(b,a){a=(a>=0)?a:this.options.length;this.options.splice(a,0,b);return this},removeItem:function(a){if(a>=0){this.options.splice(a,1)}return this},findIndexByHtml:function(b){for(var a=0;a<this.options.length;a++){if(_.has(this.options[a],"html")&&(this.options[a].html===b)){return a}}return null},findItemByHtml:function(a){return this.options[(this.findIndexByHtml(a))]},toString:function(){return"PopupMenu"}});PopupMenu.create=function _create(b,a){return new PopupMenu(b,a)};PopupMenu.make_popupmenu=function(b,c){var a=[];_.each(c,function(f,d){var e={html:d};if(f===null){e.header=true}else{if(jQuery.type(f)==="function"){e.func=f}}a.push(e)});return new PopupMenu($(b),a)};PopupMenu.convertLinksToOptions=function(c,a){c=$(c);a=a||"a";var b=[];c.find(a).each(function(g,e){var f={},d=$(g);f.html=d.text();if(d.attr("href")){var j=d.attr("href"),k=d.attr("target"),h=d.attr("confirm");f.func=function(){if((h)&&(!confirm(h))){return}switch(k){case"_parent":window.parent.location=j;break;case"_top":window.top.location=j;break;default:window.location=j}}}b.push(f)});return b};PopupMenu.fromExistingDom=function(d,c,a){d=$(d);c=$(c);var b=PopupMenu.convertLinksToOptions(c,a);c.remove();return new PopupMenu(d,b)};PopupMenu.make_popup_menus=function(c,b,d){c=c||document;b=b||"div[popupmenu]";d=d||function(e,f){return"#"+e.attr("popupmenu")};var a=[];$(c).find(b).each(function(){var e=$(this),f=$(c).find(d(e,c));a.push(PopupMenu.fromDom(f,e));f.addClass("popup")});return a};var faIconButton=function(a){a=a||{};a.tooltipConfig=a.tooltipConfig||{placement:"bottom"};a.classes=["icon-btn"].concat(a.classes||[]);if(a.disabled){a.classes.push("disabled")}var b=['<a class="',a.classes.join(" "),'"',((a.title)?(' title="'+a.title+'"'):("")),((!a.disabled&&a.target)?(' target="'+a.target+'"'):("")),' href="',((!a.disabled&&a.href)?(a.href):("javascript:void(0);")),'">','<span class="fa ',a.faIcon,'"></span>',"</a>"].join("");var c=$(b).tooltip(a.tooltipConfig);if(_.isFunction(a.onclick)){c.click(a.onclick)}return c};function LoadingIndicator(a,c){var b=this;c=jQuery.extend({cover:false},c||{});function d(){var e=['<div class="loading-indicator">','<div class="loading-indicator-text">','<span class="fa fa-spinner fa-spin fa-lg"></span>','<span class="loading-indicator-message">loading...</span>',"</div>","</div>"].join("\n");var g=$(e).hide().css(c.css||{position:"fixed"}),f=g.children(".loading-indicator-text");if(c.cover){g.css({"z-index":2,top:a.css("top"),bottom:a.css("bottom"),left:a.css("left"),right:a.css("right"),opacity:0.5,"background-color":"white","text-align":"center"});f=g.children(".loading-indicator-text").css({"margin-top":"20px"})}else{f=g.children(".loading-indicator-text").css({margin:"12px 0px 0px 10px",opacity:"0.85",color:"grey"});f.children(".loading-indicator-message").css({margin:"0px 8px 0px 0px","font-style":"italic"})}return g}b.show=function(f,e,g){f=f||"loading...";e=e||"fast";a.parent().find(".loading-indicator").remove();b.$indicator=d().insertBefore(a);b.message(f);b.$indicator.fadeIn(e,g);return b};b.message=function(e){b.$indicator.find("i").text(e)};b.hide=function(e,f){e=e||"fast";if(b.$indicator&&b.$indicator.size()){b.$indicator.fadeOut(e,function(){b.$indicator.remove();if(f){f()}})}else{if(f){f()}}return b};return b}(function(){var b=window._l||function(d){return d};function a(k,q){var e=27,n=13,d=$(k),f=true,h={initialVal:"",name:"search",placeholder:"search",classes:"",onclear:function(){},onfirstsearch:null,onsearch:function(r){},minSearchLen:0,escWillClear:true,oninit:function(){}};function j(r){var s=$(this).parent().children("input");s.focus().val("").trigger("clear:searchInput");q.onclear()}function p(s,r){$(this).trigger("search:searchInput",r);if(typeof q.onfirstsearch==="function"&&f){f=false;q.onfirstsearch(r)}else{q.onsearch(r)}}function g(){return['<input type="text" name="',q.name,'" placeholder="',q.placeholder,'" ','class="search-query ',q.classes,'" ',"/>"].join("")}function m(){return $(g()).focus(function(r){$(this).select()}).keyup(function(s){s.preventDefault();s.stopPropagation();if(!$(this).val()){$(this).blur()}if(s.which===e&&q.escWillClear){j.call(this,s)}else{var r=$(this).val();if((s.which===n)||(q.minSearchLen&&r.length>=q.minSearchLen)){p.call(this,s,r)}else{if(!r.length){j.call(this,s)}}}}).on("change",function(r){p.call(this,r,$(this).val())}).val(q.initialVal)}function l(){return $(['<span class="search-clear fa fa-times-circle" ','title="',b("clear search (esc)"),'"></span>'].join("")).tooltip({placement:"bottom"}).click(function(r){j.call(this,r)})}function o(){return $(['<span class="search-loading fa fa-spinner fa-spin" ','title="',b("loading..."),'"></span>'].join("")).hide().tooltip({placement:"bottom"})}function i(){d.find(".search-loading").toggle();d.find(".search-clear").toggle()}if(jQuery.type(q)==="string"){if(q==="toggle-loading"){i()}return d}if(jQuery.type(q)==="object"){q=jQuery.extend(true,{},h,q)}return d.addClass("search-input").prepend([m(),l(),o()])}jQuery.fn.extend({searchInput:function c(d){return this.each(function(){return a(this,d)})}})}()); \ No newline at end of file diff -r 0fb0c56af3cf25bb8c3bb366d34c6aedcbb9df14 -r 8e98c3d9b9a8bc3cabff60c67367fbaf5b328320 templates/webapps/galaxy/history/view.mako --- a/templates/webapps/galaxy/history/view.mako +++ b/templates/webapps/galaxy/history/view.mako @@ -65,8 +65,7 @@ ## ---------------------------------------------------------------------------- <%def name="javascripts()"> -${parent.javascripts()} - + ${parent.javascripts()} </%def> ## ---------------------------------------------------------------------------- @@ -144,7 +143,7 @@ window.location = "${ switch_to_url }"; } }); - + $( '#import' ).modeButton({ switchModesOnClick : false, initialMode : "${ 'with_deleted' if show_deleted else 'without_deleted' }", @@ -175,8 +174,16 @@ ({ location: 'mvc/history/history-panel', className: 'HistoryPanel' }); require.config({ - baseUrl : "${h.url_for( '/static/scripts' )}" - })([ 'mvc/user/user-model', panelToUse.location, 'utils/localization' ], function( user, panelMod, _l ){ + baseUrl : "${h.url_for( '/static/scripts' )}", + paths : { + 'jquery' : 'libs/jquery/jquery' + } + })([ + 'mvc/user/user-model', + panelToUse.location, + 'utils/localization', + 'jq-plugins/ui/mode-button' + ], function( user, panelMod, _l ){ $(function(){ setUpBehaviors(); if( hasMasthead ){ Repository URL: https://bitbucket.org/galaxy/galaxy-central/ -- This is a commit notification from bitbucket.org. You are receiving this because you have the service enabled, addressing the recipient of this email.