1 new commit in galaxy-central: https://bitbucket.org/galaxy/galaxy-central/commits/149f0fc73fae/ changeset: 149f0fc73fae user: jgoecks date: 2013-01-28 20:02:25 summary: Grid framework refactoring to increase speed and ease of debugging: (1) create and use Backbone object for grid; (2) move grid javascript to its own file; (3) remove webapp parameter; (4) augment search box style so that search button does not wrap. Pack scripts. affected #: 9 files diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 lib/galaxy/web/framework/helpers/grids.py --- a/lib/galaxy/web/framework/helpers/grids.py +++ b/lib/galaxy/web/framework/helpers/grids.py @@ -16,7 +16,6 @@ """ Specifies the content and format of a grid (data table). """ - webapp = None title = "" exposed = True model_class = None @@ -56,7 +55,6 @@ def __call__( self, trans, **kwargs ): # Get basics. # FIXME: pretty sure this is only here to pass along, can likely be eliminated - webapp = trans.webapp.name status = kwargs.get( 'status', None ) message = kwargs.get( 'message', None ) # Build a base filter and sort key that is the combination of the saved state and defaults. @@ -229,7 +227,6 @@ params = cur_filter_dict.copy() params['sort'] = sort_key params['async'] = ( 'async' in kwargs ) - params['webapp'] = webapp trans.log_action( trans.get_user(), unicode( "grid.view" ), context, params ) # Render grid. def url( *args, **kwargs ): @@ -273,7 +270,6 @@ status = status, message = message, use_panels=self.use_panels, - webapp=webapp, show_item_checkboxes = ( self.show_item_checkboxes or kwargs.get( 'show_item_checkboxes', '' ) in [ 'True', 'true' ] ), # Pass back kwargs so that grid template can set and use args without diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 static/june_2007_style/base.less --- a/static/june_2007_style/base.less +++ b/static/june_2007_style/base.less @@ -1085,6 +1085,7 @@ vertical-align: bottom; display: inline-block; padding: 0; + white-space: nowrap; // border: 1px solid #aaa; } .gray-background { diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 static/june_2007_style/blue/base.css --- a/static/june_2007_style/blue/base.css +++ b/static/june_2007_style/blue/base.css @@ -976,7 +976,7 @@ #advanced-search table{border-collapse:separate;} .delete-search-icon{background:url(../images/delete_tag_icon_gray.png) center no-repeat;display:inline-block;width:10px;cursor:pointer;height:18px;vertical-align:middle;margin-left:2px;} .search-box-input{border:0;float:left;outline:medium none;font-style:italic;font-size:inherit;} -.search-box{vertical-align:bottom;display:inline-block;padding:0;} +.search-box{vertical-align:bottom;display:inline-block;padding:0;white-space:nowrap;} .gray-background{background-color:#DDDDDD;} .loading-elt-overlay{background-color:white;opacity:0.5;width:100%;height:100%;z-index:14000;position:fixed;display:none;} div.odd_row{background:#dadfef;} diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 static/scripts/galaxy.grids.js --- /dev/null +++ b/static/scripts/galaxy.grids.js @@ -0,0 +1,549 @@ +// External dependencies (for module management eventually): jQuery, Backbone, underscore + +// This is necessary so that, when nested arrays are used in ajax/post/get methods, square brackets ('[]') are +// not appended to the identifier of a nested array. +jQuery.ajaxSettings.traditional = true; + +// Initialize grid objects on load. +$(document).ready(function() { + init_grid_elements(); + init_grid_controls(); + + // Initialize text filters to select text on click and use normal font when user is typing. + $('input[type=text]').each(function() { + $(this).click(function() { $(this).select(); } ) + .keyup(function () { $(this).css("font-style", "normal"); }); + }); +}); + +/** + * A Galaxy grid. + */ +var Grid = Backbone.Model.extend({ + defaults: { + url_base: '', + async: false, + async_ops: [], + categorical_filters: [], + filters: {}, + sort_key: null, + show_item_checkboxes: false, + cur_page: 1, + num_pages: 1, + operation: undefined, + item_ids: undefined + }, + + /** + * Return true if operation can be done asynchronously. + */ + can_async_op: function(op) { + return _.indexOf(this.attributes.async_ops, op) !== -1; + }, + + /** + * Add filtering criterion. + */ + add_filter: function(key, value, append) { + // Update URL arg with new condition. + if (append) { + // Update or append value. + var cur_val = this.attributes.key, + new_val; + if (cur_val === null || cur_val === undefined) { + new_val = value; + } + else if (typeof(cur_val) == "string") { + if (cur_val == "All") { + new_val = value; + } else { + // Replace string with array. + var values = []; + values[0] = cur_val; + values[1] = value; + new_val = values; + } + } + else { + // Current value is an array. + new_val = cur_val; + new_val.push(value); + } + this.attributes.filters[key] = new_val; + } + else { + // Replace value. + this.attributes.filters[key] = value; + } + }, + + /** + * Remove filtering criterion. + */ + remove_filter: function(key, condition) { + var cur_val = this.attributes.filters[key]; + if (cur_val === null || cur_val === undefined) { + return false; + } + + var removed = true; + if (typeof(cur_val) === "string") { + if (cur_val == "All") { + // Unexpected. Throw error? + removed = false; + } + else { + // Remove condition. + delete this.attributes.filters[key]; + } + } + else { + // Filter contains an array of conditions. + var condition_index = _.indexOf(cur_val, condition); + if (condition_index !== -1) { + cur_val.splice(condition_index, 1); + } + else { + removed = false; + } + } + + return removed; + }, + + /** + * Returns URL data for obtaining a new grid. + */ + get_url_data: function() { + var url_data = { + async: this.attributes.async, + sort: this.attributes.sort_key, + page: this.attributes.cur_page, + show_item_checkboxes: this.attributes.show_item_checkboxes, + operation: this.attributes.operation, + id: this.attributes.item_ids + }; + + // Add filter arguments to data, placing "f-" in front of all arguments. + // FIXME: when underscore updated, use pairs function(). + var self = this; + _.each(_.keys(self.attributes.filters), function(k) { + url_data['f-' + k] = self.attributes.filters[k]; + }); + + return url_data; + } +}); + +// +// Code to handle grid operations: filtering, sorting, paging, and operations. +// + +// Init operation buttons. +function init_operation_buttons() { + // Initialize operation buttons. + $('input[name=operation]:submit').each(function() { + $(this).click( function() { + var operation_name = $(this).val(); + // For some reason, $('input[name=id]:checked').val() does not return all ids for checked boxes. + // The code below performs this function. + var item_ids = []; + $('input[name=id]:checked').each(function() { + item_ids.push( $(this).val() ); + }); + do_operation(operation_name, item_ids); + }); + }); +} + +// Initialize grid controls +function init_grid_controls() { + init_operation_buttons(); + + // Initialize submit image elements. + $('.submit-image').each( function() { + // On mousedown, add class to simulate click. + $(this).mousedown( function() { + $(this).addClass('gray-background'); + }); + + // On mouseup, add class to simulate click. + $(this).mouseup( function() { + $(this).removeClass('gray-background'); + }); + }); + + // Initialize sort links. + $('.sort-link').each( function() { + $(this).click( function() { + set_sort_condition( $(this).attr('sort_key') ); + return false; + }); + }); + + // Initialize page links. + $('.page-link > a').each( function() { + $(this).click( function() { + set_page( $(this).attr('page_num') ); + return false; + }); + }); + + // Initialize categorical filters. + $('.categorical-filter > a').each( function() { + $(this).click( function() { + set_categorical_filter( $(this).attr('filter_key'), $(this).attr('filter_val') ); + return false; + }); + }); + + // Initialize text filters. + $('.text-filter-form').each( function() { + $(this).submit( function() { + var column_key = $(this).attr('column_key'); + var text_input_obj = $('#input-' + column_key + '-filter'); + var text_input = text_input_obj.val(); + text_input_obj.val(''); + add_filter_condition(column_key, text_input, true); + return false; + }); + }); + + // Initialize autocomplete for text inputs in search UI. + var t = $("#input-tags-filter"); + if (t.length) { + t.autocomplete(history_tag_autocomplete_url, + { selectFirst: false, autoFill: false, highlight: false, mustMatch: false }); + } + + var t2 = $("#input-name-filter"); + if (t2.length) { + t2.autocomplete(history_name_autocomplete_url, + { selectFirst: false, autoFill: false, highlight: false, mustMatch: false }); + } + + // Initialize standard, advanced search toggles. + $('.advanced-search-toggle').each( function() { + $(this).click( function() { + $("#standard-search").slideToggle('fast'); + $('#advanced-search').slideToggle('fast'); + return false; + }); + }); +} + +// Initialize grid elements. +function init_grid_elements() { + // Initialize grid selection checkboxes. + $(".grid").each( function() { + var checkboxes = $(this).find("input.grid-row-select-checkbox"); + var check_count = $(this).find("span.grid-selected-count"); + var update_checked = function() { + check_count.text( $(checkboxes).filter(":checked").length ); + }; + + $(checkboxes).each( function() { + $(this).change(update_checked); + }); + update_checked(); + }); + + // Initialize item labels. + $(".label").each( function() { + // If href has an operation in it, do operation when clicked. Otherwise do nothing. + var href = $(this).attr('href'); + if ( href !== undefined && href.indexOf('operation=') != -1 ) { + $(this).click( function() { + do_operation_from_href( $(this).attr('href') ); + return false; + }); + } + }); + + // Initialize ratings. + $('.community_rating_star').rating({}); + + // Initialize item menu operations. + make_popup_menus(); +} + +// Go back to page one; this is useful when a filter is applied. +function go_page_one() { + // Need to go back to page 1 if not showing all. + var cur_page = grid.get('cur_page'); + if (cur_page !== null && cur_page !== undefined && cur_page !== 'all') { + grid.set('cur_page', 1); + } +} + +// Add a condition to the grid filter; this adds the condition and refreshes the grid. +function add_filter_condition(name, value, append) { + // Do nothing is value is empty. + if (value === "") { + return false; + } + + // Add condition to grid. + grid.add_filter(name, value, append); + + // Add button that displays filter and provides a button to delete it. + var t = $("<span>" + value + "<a href='javascript:void(0);'><span class='delete-search-icon' /></a></span>"); + t.addClass('text-filter-val'); + t.click(function() { + // Remove filter condition. + grid.remove_filter(name, value); + + // Remove visible element. + $(this).remove(); + + go_page_one(); + update_grid(); + }); + + var container = $('#' + name + "-filtering-criteria"); + container.append(t); + + go_page_one(); + update_grid(); +} + +// Add tag to grid filter. +function add_tag_to_grid_filter(tag_name, tag_value) { + // Put tag name and value together. + var tag = tag_name + (tag_value !== undefined && tag_value !== "" ? ":" + tag_value : ""); + $('#advanced-search').show('fast'); + add_filter_condition("tags", tag, true); +} + +// Set sort condition for grid. +function set_sort_condition(col_key) { + // Set new sort condition. New sort is col_key if sorting new column; if reversing sort on + // currently sorted column, sort is reversed. + var cur_sort = grid.get('sort_key'); + var new_sort = col_key; + if (cur_sort.indexOf(col_key) !== -1) { + // Reverse sort. + if (cur_sort.substring(0,1) !== '-') { + new_sort = '-' + col_key; + } else { + // Sort reversed by using just col_key. + } + } + + // Remove sort arrows elements. + $('.sort-arrow').remove(); + + // Add sort arrow element to new sort column. + var sort_arrow = (new_sort.substring(0,1) == '-') ? "↑" : "↓"; + var t = $("<span>" + sort_arrow + "</span>").addClass('sort-arrow'); + var th = $("#" + col_key + '-header'); + th.append(t); + + // Update grid. + grid.set('sort_key', new_sort); + go_page_one(); + update_grid(); +} + +// Set new value for categorical filter. +function set_categorical_filter(name, new_value) { + // Update filter hyperlinks to reflect new filter value. + var category_filter = grid.get('categorical_filters')[name], + cur_value = grid.get('filters')[name]; + $("." + name + "-filter").each( function() { + var text = $.trim( $(this).text() ); + var filter = category_filter[text]; + var filter_value = filter[name]; + if (filter_value == new_value) { + // Remove filter link since grid will be using this filter. It is assumed that + // this element has a single child, a hyperlink/anchor with text. + $(this).empty(); + $(this).addClass("current-filter"); + $(this).append(text); + } else if (filter_value == cur_value) { + // Add hyperlink for this filter since grid will no longer be using this filter. It is assumed that + // this element has a single child, a hyperlink/anchor. + $(this).empty(); + var t = $("<a href='#'>" + text + "</a>"); + t.click(function() { + set_categorical_filter( name, filter_value ); + }); + $(this).removeClass("current-filter"); + $(this).append(t); + } + }); + + // Update grid. + grid.add_filter(name, new_value); + go_page_one(); + update_grid(); +} + +// Set page to view. +function set_page(new_page) { + // Update page hyperlink to reflect new page. + $(".page-link").each( function() { + var id = $(this).attr('id'), + page_num = parseInt( id.split("-")[2], 10 ), // Id has form 'page-link-<page_num> + cur_page = grid.get('cur_page'), + text; + if (page_num === new_page) { + // Remove link to page since grid will be on this page. It is assumed that + // this element has a single child, a hyperlink/anchor with text. + text = $(this).children().text(); + $(this).empty(); + $(this).addClass("inactive-link"); + $(this).text(text); + } + else if (page_num === cur_page) { + // Add hyperlink to this page since grid will no longer be on this page. It is assumed that + // this element has a single child, a hyperlink/anchor. + text = $(this).text(); + $(this).empty(); + $(this).removeClass("inactive-link"); + var t = $("<a href='#'>" + text + "</a>"); + t.click(function() { + set_page(page_num); + }); + $(this).append(t); + } + }); + + var maintain_page_links = true; + if (new_page === "all") { + grid.set('cur_page', new_page); + maintain_page_links = false; + } else { + grid.set('cur_page', parseInt(new_page, 10)); + } + update_grid(maintain_page_links); +} + +// Perform a grid operation. +function do_operation(operation, item_ids) { + operation = operation.toLowerCase(); + + // Update grid. + grid.set({ + operation: operation, + item_ids: item_ids + }); + + // Do operation. If operation cannot be performed asynchronously, redirect to location. + if (grid.can_async_op(operation)) { + update_grid(true); + } + else { + go_to_URL(); + } +} + +// Perform a hyperlink click that initiates an operation. If there is no operation, ignore click. +function do_operation_from_href(href) { + // Get operation, id in hyperlink's href. + var href_parts = href.split("?"); + if (href_parts.length > 1) { + var href_parms_str = href_parts[1]; + var href_parms = href_parms_str.split("&"); + var operation = null; + var id = -1; + for (var index = 0; index < href_parms.length; index++) { + if (href_parms[index].indexOf('operation') != -1) { + // Found operation parm; get operation value. + operation = href_parms[index].split('=')[1]; + } else if (href_parms[index].indexOf('id') != -1) { + // Found id parm; get id value. + id = href_parms[index].split('=')[1]; + } + } + // Do operation. + do_operation(operation, id); + return false; + } +} + +// Navigate window to the URL defined by url_args. This method can be used to short-circuit grid AJAXing. +function go_to_URL() { + // Not async request. + grid.set('async', false); + + // Go. + window.location = grid.get('url_base') + "?" + $.param(grid.get_url_data()); +} + +// Update grid. +function update_grid(maintain_page_links) { + // If grid is not using async, then go to URL. + if (!grid.get('async')) { + go_to_URL(); + } + + // If there's an operation, do POST; otherwise, do GET. + var method = (grid.get('operation') ? "POST" : "GET" ); + $('.loading-elt-overlay').show(); // Show overlay to indicate loading and prevent user actions. + $.ajax({ + type: method, + url: grid.get('url_base'), + data: grid.get_url_data(), + error: function() { alert( "Grid refresh failed" ); }, + success: function(response_text) { + // HACK: use a simple string to separate the elements in the + // response: (1) table body; (2) number of pages in table; and (3) message. + var parsed_response_text = response_text.split("*****"); + + // Update grid body and footer. + $('#grid-table-body').html(parsed_response_text[0]); + // FIXME: this does not work at all; what's needed is a function + // that updates page links when number of pages changes. + $('#grid-table-footer').html(parsed_response_text[1]); + + // Trigger custom event to indicate grid body has changed. + $('#grid-table-body').trigger('update'); + + // Init grid. + init_grid_elements(); + init_operation_buttons(); + make_popup_menus(); + + // Hide loading overlay. + $('.loading-elt-overlay').hide(); + + // Show message if there is one. + var message = $.trim( parsed_response_text[2] ); + if (message !== "") { + $('#grid-message').html( message ).show(); + setTimeout( function() { $('#grid-message').hide(); }, 5000); + } + }, + complete: function() { + // Clear grid of transient request attributes. + grid.set({ + operation: undefined, + item_ids: undefined + }); + } + }); +} + +function check_all_items() { + var chk_all = document.getElementById('check_all'), + checks = document.getElementsByTagName('input'), + total = 0, + i; + if ( chk_all.checked === true ) { + for ( i=0; i < checks.length; i++ ) { + if ( checks[i].name.indexOf( 'id' ) !== -1) { + checks[i].checked = true; + total++; + } + } + } + else { + for ( i=0; i < checks.length; i++ ) { + if ( checks[i].name.indexOf( 'id' ) !== -1) { + checks[i].checked = false; + } + } + } + init_grid_elements(); +} \ No newline at end of file diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 static/scripts/packed/galaxy.grids.js --- /dev/null +++ b/static/scripts/packed/galaxy.grids.js @@ -0,0 +1,1 @@ +jQuery.ajaxSettings.traditional=true;$(document).ready(function(){init_grid_elements();init_grid_controls();$("input[type=text]").each(function(){$(this).click(function(){$(this).select()}).keyup(function(){$(this).css("font-style","normal")})})});var Grid=Backbone.Model.extend({defaults:{url_base:"",async:false,async_ops:[],categorical_filters:[],filters:{},sort_key:null,show_item_checkboxes:false,cur_page:1,num_pages:1,operation:undefined,item_ids:undefined},can_async_op:function(a){return _.indexOf(this.attributes.async_ops,a)!==-1},add_filter:function(e,f,b){if(b){var c=this.attributes.key,a;if(c===null||c===undefined){a=f}else{if(typeof(c)=="string"){if(c=="All"){a=f}else{var d=[];d[0]=c;d[1]=f;a=d}}else{a=c;a.push(f)}}this.attributes.filters[e]=a}else{this.attributes.filters[e]=f}},remove_filter:function(b,e){var a=this.attributes.filters[b];if(a===null||a===undefined){return false}var d=true;if(typeof(a)==="string"){if(a=="All"){d=false}else{delete this.attributes.filters[b]}}else{var c=_.indexOf(a,e);if(c!==-1){a.splice(c,1)}else{d=false}}return d},get_url_data:function(){var a={async:this.attributes.async,sort:this.attributes.sort_key,page:this.attributes.cur_page,show_item_checkboxes:this.attributes.show_item_checkboxes,operation:this.attributes.operation,id:this.attributes.item_ids};var b=this;_.each(_.keys(b.attributes.filters),function(c){a["f-"+c]=b.attributes.filters[c]});return a}});function init_operation_buttons(){$("input[name=operation]:submit").each(function(){$(this).click(function(){var b=$(this).val();var a=[];$("input[name=id]:checked").each(function(){a.push($(this).val())});do_operation(b,a)})})}function init_grid_controls(){init_operation_buttons();$(".submit-image").each(function(){$(this).mousedown(function(){$(this).addClass("gray-background")});$(this).mouseup(function(){$(this).removeClass("gray-background")})});$(".sort-link").each(function(){$(this).click(function(){set_sort_condition($(this).attr("sort_key"));return false})});$(".page-link > a").each(function(){$(this).click(function(){set_page($(this).attr("page_num"));return false})});$(".categorical-filter > a").each(function(){$(this).click(function(){set_categorical_filter($(this).attr("filter_key"),$(this).attr("filter_val"));return false})});$(".text-filter-form").each(function(){$(this).submit(function(){var d=$(this).attr("column_key");var c=$("#input-"+d+"-filter");var e=c.val();c.val("");add_filter_condition(d,e,true);return false})});var a=$("#input-tags-filter");if(a.length){a.autocomplete(history_tag_autocomplete_url,{selectFirst:false,autoFill:false,highlight:false,mustMatch:false})}var b=$("#input-name-filter");if(b.length){b.autocomplete(history_name_autocomplete_url,{selectFirst:false,autoFill:false,highlight:false,mustMatch:false})}$(".advanced-search-toggle").each(function(){$(this).click(function(){$("#standard-search").slideToggle("fast");$("#advanced-search").slideToggle("fast");return false})})}function init_grid_elements(){$(".grid").each(function(){var b=$(this).find("input.grid-row-select-checkbox");var a=$(this).find("span.grid-selected-count");var c=function(){a.text($(b).filter(":checked").length)};$(b).each(function(){$(this).change(c)});c()});$(".label").each(function(){var a=$(this).attr("href");if(a!==undefined&&a.indexOf("operation=")!=-1){$(this).click(function(){do_operation_from_href($(this).attr("href"));return false})}});$(".community_rating_star").rating({});make_popup_menus()}function go_page_one(){var a=grid.get("cur_page");if(a!==null&&a!==undefined&&a!=="all"){grid.set("cur_page",1)}}function add_filter_condition(c,e,a){if(e===""){return false}grid.add_filter(c,e,a);var d=$("<span>"+e+"<a href='javascript:void(0);'><span class='delete-search-icon' /></a></span>");d.addClass("text-filter-val");d.click(function(){grid.remove_filter(c,e);$(this).remove();go_page_one();update_grid()});var b=$("#"+c+"-filtering-criteria");b.append(d);go_page_one();update_grid()}function add_tag_to_grid_filter(c,b){var a=c+(b!==undefined&&b!==""?":"+b:"");$("#advanced-search").show("fast");add_filter_condition("tags",a,true)}function set_sort_condition(f){var e=grid.get("sort_key");var d=f;if(e.indexOf(f)!==-1){if(e.substring(0,1)!=="-"){d="-"+f}else{}}$(".sort-arrow").remove();var c=(d.substring(0,1)=="-")?"↑":"↓";var a=$("<span>"+c+"</span>").addClass("sort-arrow");var b=$("#"+f+"-header");b.append(a);grid.set("sort_key",d);go_page_one();update_grid()}function set_categorical_filter(b,d){var a=grid.get("categorical_filters")[b],c=grid.get("filters")[b];$("."+b+"-filter").each(function(){var h=$.trim($(this).text());var f=a[h];var g=f[b];if(g==d){$(this).empty();$(this).addClass("current-filter");$(this).append(h)}else{if(g==c){$(this).empty();var e=$("<a href='#'>"+h+"</a>");e.click(function(){set_categorical_filter(b,g)});$(this).removeClass("current-filter");$(this).append(e)}}});grid.add_filter(b,d);go_page_one();update_grid()}function set_page(a){$(".page-link").each(function(){var g=$(this).attr("id"),e=parseInt(g.split("-")[2],10),c=grid.get("cur_page"),f;if(e===a){f=$(this).children().text();$(this).empty();$(this).addClass("inactive-link");$(this).text(f)}else{if(e===c){f=$(this).text();$(this).empty();$(this).removeClass("inactive-link");var d=$("<a href='#'>"+f+"</a>");d.click(function(){set_page(e)});$(this).append(d)}}});var b=true;if(a==="all"){grid.set("cur_page",a);b=false}else{grid.set("cur_page",parseInt(a,10))}update_grid(b)}function do_operation(b,a){b=b.toLowerCase();grid.set({operation:b,item_ids:a});if(grid.can_async_op(b)){update_grid(true)}else{go_to_URL()}}function do_operation_from_href(c){var f=c.split("?");if(f.length>1){var a=f[1];var e=a.split("&");var b=null;var g=-1;for(var d=0;d<e.length;d++){if(e[d].indexOf("operation")!=-1){b=e[d].split("=")[1]}else{if(e[d].indexOf("id")!=-1){g=e[d].split("=")[1]}}}do_operation(b,g);return false}}function go_to_URL(){grid.set("async",false);window.location=grid.get("url_base")+"?"+$.param(grid.get_url_data())}function update_grid(a){if(!grid.get("async")){go_to_URL()}var b=(grid.get("operation")?"POST":"GET");$(".loading-elt-overlay").show();$.ajax({type:b,url:grid.get("url_base"),data:grid.get_url_data(),error:function(){alert("Grid refresh failed")},success:function(d){var c=d.split("*****");$("#grid-table-body").html(c[0]);$("#grid-table-footer").html(c[1]);$("#grid-table-body").trigger("update");init_grid_elements();init_operation_buttons();make_popup_menus();$(".loading-elt-overlay").hide();var e=$.trim(c[2]);if(e!==""){$("#grid-message").html(e).show();setTimeout(function(){$("#grid-message").hide()},5000)}},complete:function(){grid.set({operation:undefined,item_ids:undefined})}})}function check_all_items(){var a=document.getElementById("check_all"),b=document.getElementsByTagName("input"),d=0,c;if(a.checked===true){for(c=0;c<b.length;c++){if(b[c].name.indexOf("id")!==-1){b[c].checked=true;d++}}}else{for(c=0;c<b.length;c++){if(b[c].name.indexOf("id")!==-1){b[c].checked=false}}}init_grid_elements()}; \ No newline at end of file diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 static/scripts/packed/mvc/dataset/hda-base.js --- a/static/scripts/packed/mvc/dataset/hda-base.js +++ b/static/scripts/packed/mvc/dataset/hda-base.js @@ -1,1 +1,1 @@ -var HDABaseView=BaseView.extend(LoggableMixin).extend({tagName:"div",className:"historyItemContainer",initialize:function(a){if(a.logger){this.logger=this.model.logger=a.logger}this.log(this+".initialize:",a);this.defaultPrimaryActionButtonRenderers=[this._render_showParamsButton];if(!a.urlTemplates){throw ("HDAView needs urlTemplates on initialize")}this.urlTemplates=a.urlTemplates;this.expanded=a.expanded||false;this.model.bind("change",this.render,this)},render:function(){var b=this,e=this.model.get("id"),c=this.model.get("state"),a=$("<div/>").attr("id","historyItem-"+e),d=(this.$el.children().size()===0);this.$el.attr("id","historyItemContainer-"+e);this.urls=this._renderUrls(this.urlTemplates,this.model.toJSON());a.addClass("historyItemWrapper").addClass("historyItem").addClass("historyItem-"+c);a.append(this._render_warnings());a.append(this._render_titleBar());this._setUpBehaviors(a);this.body=$(this._render_body());a.append(this.body);this.$el.fadeOut("fast",function(){b.$el.children().remove();b.$el.append(a).fadeIn("fast",function(){b.log(b+" rendered:",b.$el);var f="rendered";if(d){f+=":initial"}else{if(b.model.inReadyState()){f+=":ready"}}b.trigger(f)})});return this},_renderUrls:function(d,a){var b=this,c={};_.each(d,function(e,f){if(_.isObject(e)){c[f]=b._renderUrls(e,a)}else{if(f==="meta_download"){c[f]=b._renderMetaDownloadUrls(e,a)}else{try{c[f]=_.template(e,a)}catch(g){throw (b+"._renderUrls error: "+g+"\n rendering:"+e+"\n with "+JSON.stringify(a))}}}});return c},_renderMetaDownloadUrls:function(b,a){return _.map(a.meta_files,function(c){return{url:_.template(b,{id:a.id,file_type:c.file_type}),file_type:c.file_type}})},_setUpBehaviors:function(a){a=a||this.$el;make_popup_menus(a);a.find(".tooltip").tooltip({placement:"bottom"})},_render_warnings:function(){return $(jQuery.trim(HDABaseView.templates.messages(this.model.toJSON())))},_render_titleBar:function(){var a=$('<div class="historyItemTitleBar" style="overflow: hidden"></div>');a.append(this._render_titleButtons());a.append('<span class="state-icon"></span>');a.append(this._render_titleLink());return a},_render_titleButtons:function(){var a=$('<div class="historyItemButtons"></div>');a.append(this._render_displayButton());return a},_render_displayButton:function(){if((!this.model.inReadyState())||(this.model.get("state")===HistoryDatasetAssociation.STATES.NOT_VIEWABLE)||(!this.model.get("accessible"))){this.displayButton=null;return null}var a={icon_class:"display",target:"galaxy_main"};if(this.model.get("purged")){a.enabled=false;a.title=_l("Cannot display datasets removed from disk")}else{a.title=_l("Display data in browser");a.href=this.urls.display}this.displayButton=new IconButtonView({model:new IconButton(a)});return this.displayButton.render().$el},_render_titleLink:function(){return $(jQuery.trim(HDABaseView.templates.titleLink(_.extend(this.model.toJSON(),{urls:this.urls}))))},_render_hdaSummary:function(){var a=_.extend(this.model.toJSON(),{urls:this.urls});return HDABaseView.templates.hdaSummary(a)},_render_primaryActionButtons:function(c){var a=this,b=$("<div/>").attr("id","primary-actions-"+this.model.get("id"));_.each(c,function(d){b.append(d.call(a))});return b},_render_downloadButton:function(){if(this.model.get("purged")||!this.model.hasData()){return null}var a=HDABaseView.templates.downloadLinks(_.extend(this.model.toJSON(),{urls:this.urls}));return $(a)},_render_showParamsButton:function(){this.showParamsButton=new IconButtonView({model:new IconButton({title:_l("View details"),href:this.urls.show_params,target:"galaxy_main",icon_class:"information"})});return this.showParamsButton.render().$el},_render_displayApps:function(){if(!this.model.hasData()){return null}var a=$("<div/>").addClass("display-apps");if(!_.isEmpty(this.model.get("display_types"))){a.append(HDABaseView.templates.displayApps({displayApps:this.model.get("display_types")}))}if(!_.isEmpty(this.model.get("display_apps"))){a.append(HDABaseView.templates.displayApps({displayApps:this.model.get("display_apps")}))}return a},_render_peek:function(){if(!this.model.get("peek")){return null}return $("<div/>").append($("<pre/>").attr("id","peek"+this.model.get("id")).addClass("peek").append(this.model.get("peek")))},_render_body:function(){var a=$("<div/>").attr("id","info-"+this.model.get("id")).addClass("historyItemBody").attr("style","display: none");if(this.expanded){this._render_body_html(a);a.show()}return a},_render_body_html:function(a){a.html("");switch(this.model.get("state")){case HistoryDatasetAssociation.STATES.NEW:break;case HistoryDatasetAssociation.STATES.NOT_VIEWABLE:this._render_body_not_viewable(a);break;case HistoryDatasetAssociation.STATES.UPLOAD:this._render_body_uploading(a);break;case HistoryDatasetAssociation.STATES.PAUSED:this._render_body_paused(a);break;case HistoryDatasetAssociation.STATES.QUEUED:this._render_body_queued(a);break;case HistoryDatasetAssociation.STATES.RUNNING:this._render_body_running(a);break;case HistoryDatasetAssociation.STATES.ERROR:this._render_body_error(a);break;case HistoryDatasetAssociation.STATES.DISCARDED:this._render_body_discarded(a);break;case HistoryDatasetAssociation.STATES.SETTING_METADATA:this._render_body_setting_metadata(a);break;case HistoryDatasetAssociation.STATES.EMPTY:this._render_body_empty(a);break;case HistoryDatasetAssociation.STATES.FAILED_METADATA:this._render_body_failed_metadata(a);break;case HistoryDatasetAssociation.STATES.OK:this._render_body_ok(a);break;default:a.append($('<div>Error: unknown dataset state "'+this.model.get("state")+'".</div>'))}a.append('<div style="clear: both"></div>');this._setUpBehaviors(a)},_render_body_not_viewable:function(a){a.append($("<div>"+_l("You do not have permission to view dataset")+".</div>"))},_render_body_uploading:function(a){a.append($("<div>"+_l("Dataset is uploading")+"</div>"))},_render_body_queued:function(a){a.append($("<div>"+_l("Job is waiting to run")+".</div>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_paused:function(a){a.append($("<div>"+_l("Job is paused. Use the history menu to unpause")+".</div>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_running:function(a){a.append("<div>"+_l("Job is currently running")+".</div>");a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_error:function(a){if(!this.model.get("purged")){a.append($("<div>"+this.model.get("misc_blurb")+"</div>"))}a.append((_l("An error occurred running this job")+": <i>"+$.trim(this.model.get("misc_info"))+"</i>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers.concat([this._render_downloadButton])))},_render_body_discarded:function(a){a.append("<div>"+_l("The job creating this dataset was cancelled before completion")+".</div>");a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_setting_metadata:function(a){a.append($("<div>"+_l("Metadata is being auto-detected")+".</div>"))},_render_body_empty:function(a){a.append($("<div>"+_l("No data")+": <i>"+this.model.get("misc_blurb")+"</i></div>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_failed_metadata:function(a){a.append($(HDABaseView.templates.failedMetadata(this.model.toJSON())));this._render_body_ok(a)},_render_body_ok:function(a){a.append(this._render_hdaSummary());if(this.model.isDeletedOrPurged()){a.append(this._render_primaryActionButtons([this._render_downloadButton,this._render_showParamsButton]));return}a.append(this._render_primaryActionButtons([this._render_downloadButton,this._render_showParamsButton]));a.append('<div class="clear"/>');a.append(this._render_displayApps());a.append(this._render_peek())},events:{"click .historyItemTitle":"toggleBodyVisibility"},toggleBodyVisibility:function(c,a){var b=this;this.expanded=(a===undefined)?(!this.body.is(":visible")):(a);if(this.expanded){b._render_body_html(b.body);this.body.slideDown("fast",function(){b.trigger("body-expanded",b.model.get("id"))})}else{this.body.slideUp("fast",function(){b.trigger("body-collapsed",b.model.get("id"))})}},remove:function(b){var a=this;this.$el.fadeOut("fast",function(){a.$el.remove();if(b){b()}})},toString:function(){var a=(this.model)?(this.model+""):("(no model)");return"HDABaseView("+a+")"}});HDABaseView.templates={warningMsg:Handlebars.templates["template-warningmessagesmall"],messages:Handlebars.templates["template-hda-warning-messages"],titleLink:Handlebars.templates["template-hda-titleLink"],hdaSummary:Handlebars.templates["template-hda-hdaSummary"],downloadLinks:Handlebars.templates["template-hda-downloadLinks"],failedMetadata:Handlebars.templates["template-hda-failedMetadata"],displayApps:Handlebars.templates["template-hda-displayApps"]}; \ No newline at end of file +var HDABaseView=BaseView.extend(LoggableMixin).extend({tagName:"div",className:"historyItemContainer",initialize:function(a){if(a.logger){this.logger=this.model.logger=a.logger}this.log(this+".initialize:",a);this.defaultPrimaryActionButtonRenderers=[this._render_showParamsButton];if(!a.urlTemplates){throw ("HDAView needs urlTemplates on initialize")}this.urlTemplates=a.urlTemplates;this.expanded=a.expanded||false;this.model.bind("change",this.render,this)},render:function(){var b=this,e=this.model.get("id"),c=this.model.get("state"),a=$("<div/>").attr("id","historyItem-"+e),d=(this.$el.children().size()===0);this.$el.attr("id","historyItemContainer-"+e);this.urls=this._renderUrls(this.urlTemplates,this.model.toJSON());a.addClass("historyItemWrapper").addClass("historyItem").addClass("historyItem-"+c);a.append(this._render_warnings());a.append(this._render_titleBar());this._setUpBehaviors(a);this.body=$(this._render_body());a.append(this.body);this.$el.fadeOut("fast",function(){b.$el.children().remove();b.$el.append(a).fadeIn("fast",function(){b.log(b+" rendered:",b.$el);var f="rendered";if(d){f+=":initial"}else{if(b.model.inReadyState()){f+=":ready"}}b.trigger(f)})});return this},_renderUrls:function(d,a){var b=this,c={};_.each(d,function(e,f){if(_.isObject(e)){c[f]=b._renderUrls(e,a)}else{if(f==="meta_download"){c[f]=b._renderMetaDownloadUrls(e,a)}else{try{c[f]=_.template(e,a)}catch(g){throw (b+"._renderUrls error: "+g+"\n rendering:"+e+"\n with "+JSON.stringify(a))}}}});return c},_renderMetaDownloadUrls:function(b,a){return _.map(a.meta_files,function(c){return{url:_.template(b,{id:a.id,file_type:c.file_type}),file_type:c.file_type}})},_setUpBehaviors:function(a){a=a||this.$el;make_popup_menus(a);a.find(".tooltip").tooltip({placement:"bottom"})},_render_warnings:function(){return $(jQuery.trim(HDABaseView.templates.messages(this.model.toJSON())))},_render_titleBar:function(){var a=$('<div class="historyItemTitleBar" style="overflow: hidden"></div>');a.append(this._render_titleButtons());a.append('<span class="state-icon"></span>');a.append(this._render_titleLink());return a},_render_titleButtons:function(){var a=$('<div class="historyItemButtons"></div>');a.append(this._render_displayButton());return a},_render_displayButton:function(){if((this.model.get("state")===HistoryDatasetAssociation.STATES.NOT_VIEWABLE)||(!this.model.get("accessible"))){this.displayButton=null;return null}var a={icon_class:"display",target:"galaxy_main"};if(this.model.get("purged")){a.enabled=false;a.title=_l("Cannot display datasets removed from disk")}else{a.title=_l("Display data in browser");a.href=this.urls.display}this.displayButton=new IconButtonView({model:new IconButton(a)});return this.displayButton.render().$el},_render_titleLink:function(){return $(jQuery.trim(HDABaseView.templates.titleLink(_.extend(this.model.toJSON(),{urls:this.urls}))))},_render_hdaSummary:function(){var a=_.extend(this.model.toJSON(),{urls:this.urls});return HDABaseView.templates.hdaSummary(a)},_render_primaryActionButtons:function(c){var a=this,b=$("<div/>").attr("id","primary-actions-"+this.model.get("id"));_.each(c,function(d){b.append(d.call(a))});return b},_render_downloadButton:function(){if(this.model.get("purged")||!this.model.hasData()){return null}var a=HDABaseView.templates.downloadLinks(_.extend(this.model.toJSON(),{urls:this.urls}));return $(a)},_render_showParamsButton:function(){this.showParamsButton=new IconButtonView({model:new IconButton({title:_l("View details"),href:this.urls.show_params,target:"galaxy_main",icon_class:"information"})});return this.showParamsButton.render().$el},_render_displayApps:function(){if(!this.model.hasData()){return null}var a=$("<div/>").addClass("display-apps");if(!_.isEmpty(this.model.get("display_types"))){a.append(HDABaseView.templates.displayApps({displayApps:this.model.get("display_types")}))}if(!_.isEmpty(this.model.get("display_apps"))){a.append(HDABaseView.templates.displayApps({displayApps:this.model.get("display_apps")}))}return a},_render_peek:function(){if(!this.model.get("peek")){return null}return $("<div/>").append($("<pre/>").attr("id","peek"+this.model.get("id")).addClass("peek").append(this.model.get("peek")))},_render_body:function(){var a=$("<div/>").attr("id","info-"+this.model.get("id")).addClass("historyItemBody").attr("style","display: none");if(this.expanded){this._render_body_html(a);a.show()}return a},_render_body_html:function(a){a.html("");switch(this.model.get("state")){case HistoryDatasetAssociation.STATES.NEW:break;case HistoryDatasetAssociation.STATES.NOT_VIEWABLE:this._render_body_not_viewable(a);break;case HistoryDatasetAssociation.STATES.UPLOAD:this._render_body_uploading(a);break;case HistoryDatasetAssociation.STATES.PAUSED:this._render_body_paused(a);break;case HistoryDatasetAssociation.STATES.QUEUED:this._render_body_queued(a);break;case HistoryDatasetAssociation.STATES.RUNNING:this._render_body_running(a);break;case HistoryDatasetAssociation.STATES.ERROR:this._render_body_error(a);break;case HistoryDatasetAssociation.STATES.DISCARDED:this._render_body_discarded(a);break;case HistoryDatasetAssociation.STATES.SETTING_METADATA:this._render_body_setting_metadata(a);break;case HistoryDatasetAssociation.STATES.EMPTY:this._render_body_empty(a);break;case HistoryDatasetAssociation.STATES.FAILED_METADATA:this._render_body_failed_metadata(a);break;case HistoryDatasetAssociation.STATES.OK:this._render_body_ok(a);break;default:a.append($('<div>Error: unknown dataset state "'+this.model.get("state")+'".</div>'))}a.append('<div style="clear: both"></div>');this._setUpBehaviors(a)},_render_body_not_viewable:function(a){a.append($("<div>"+_l("You do not have permission to view dataset")+".</div>"))},_render_body_uploading:function(a){a.append($("<div>"+_l("Dataset is uploading")+"</div>"))},_render_body_queued:function(a){a.append($("<div>"+_l("Job is waiting to run")+".</div>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_paused:function(a){a.append($("<div>"+_l("Job is paused. Use the history menu to resume")+".</div>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_running:function(a){a.append("<div>"+_l("Job is currently running")+".</div>");a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_error:function(a){if(!this.model.get("purged")){a.append($("<div>"+this.model.get("misc_blurb")+"</div>"))}a.append((_l("An error occurred with this dataset")+": <i>"+$.trim(this.model.get("misc_info"))+"</i>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers.concat([this._render_downloadButton])))},_render_body_discarded:function(a){a.append("<div>"+_l("The job creating this dataset was cancelled before completion")+".</div>");a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_setting_metadata:function(a){a.append($("<div>"+_l("Metadata is being auto-detected")+".</div>"))},_render_body_empty:function(a){a.append($("<div>"+_l("No data")+": <i>"+this.model.get("misc_blurb")+"</i></div>"));a.append(this._render_primaryActionButtons(this.defaultPrimaryActionButtonRenderers))},_render_body_failed_metadata:function(a){a.append($(HDABaseView.templates.failedMetadata(_.extend(this.model.toJSON(),{urls:this.urls}))));this._render_body_ok(a)},_render_body_ok:function(a){a.append(this._render_hdaSummary());if(this.model.isDeletedOrPurged()){a.append(this._render_primaryActionButtons([this._render_downloadButton,this._render_showParamsButton]));return}a.append(this._render_primaryActionButtons([this._render_downloadButton,this._render_showParamsButton]));a.append('<div class="clear"/>');a.append(this._render_displayApps());a.append(this._render_peek())},events:{"click .historyItemTitle":"toggleBodyVisibility"},toggleBodyVisibility:function(c,a){var b=this;this.expanded=(a===undefined)?(!this.body.is(":visible")):(a);if(this.expanded){b._render_body_html(b.body);this.body.slideDown("fast",function(){b.trigger("body-expanded",b.model.get("id"))})}else{this.body.slideUp("fast",function(){b.trigger("body-collapsed",b.model.get("id"))})}},remove:function(b){var a=this;this.$el.fadeOut("fast",function(){a.$el.remove();if(b){b()}})},toString:function(){var a=(this.model)?(this.model+""):("(no model)");return"HDABaseView("+a+")"}});HDABaseView.templates={warningMsg:Handlebars.templates["template-warningmessagesmall"],messages:Handlebars.templates["template-hda-warning-messages"],titleLink:Handlebars.templates["template-hda-titleLink"],hdaSummary:Handlebars.templates["template-hda-hdaSummary"],downloadLinks:Handlebars.templates["template-hda-downloadLinks"],failedMetadata:Handlebars.templates["template-hda-failedMetadata"],displayApps:Handlebars.templates["template-hda-displayApps"]}; \ No newline at end of file diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 static/scripts/packed/mvc/history/history-model.js --- a/static/scripts/packed/mvc/history/history-model.js +++ b/static/scripts/packed/mvc/history/history-model.js @@ -1,1 +1,1 @@ -var History=BaseModel.extend(LoggableMixin).extend({defaults:{id:"",name:"",state:"",diskSize:0,deleted:false,annotation:null,message:null},urlRoot:"api/histories/",url:function(){return"api/histories/"+this.get("id")},initialize:function(a,b){this.log(this+".initialize:",a,b);this.hdas=new HDACollection();if(b&&b.length){this.hdas.reset(b);this.checkForUpdates()}},loadFromApi:function(a,c){var b=this;b.attributes.id=a;jQuery.when(jQuery.ajax("api/users/current"),b.fetch()).then(function(e,d){b.attributes.user=e[0];b.trigger("loaded:user",e[0]);b.trigger("loaded",d[0])}).then(function(){jQuery.ajax(b.url()+"/contents?"+jQuery.param({ids:b.hdaIdsFromStateIds().join(",")})).success(function(d){b.hdas.reset(d);b.checkForUpdates();b.trigger("loaded:hdas",d);if(c){callback(b)}})})},hdaIdsFromStateIds:function(){return _.reduce(_.values(this.get("state_ids")),function(b,a){return b.concat(a)})},checkForUpdates:function(a){if(this.hdas.running().length){this.stateUpdater()}else{this.trigger("ready")}return this},stateUpdater:function(){var c=this,a=this.get("state"),b=this.get("state_ids");jQuery.ajax("api/histories/"+this.get("id")).success(function(d){c.set(d);c.log("current history state:",c.get("state"),"(was)",a,"new size:",c.get("nice_size"));var e=[];_.each(_.keys(d.state_ids),function(g){var f=_.difference(d.state_ids[g],b[g]);e=e.concat(f)});if(e.length){c.updateHdas(e)}if((c.get("state")===HistoryDatasetAssociation.STATES.RUNNING)||(c.get("state")===HistoryDatasetAssociation.STATES.QUEUED)){setTimeout(function(){c.stateUpdater()},History.UPDATE_DELAY)}else{c.trigger("ready")}}).error(function(f,d,e){if(!((f.readyState===0)&&(f.status===0))){alert(_l("Error getting history updates from the server.")+"\n"+e)}})},updateHdas:function(b){var a=this;jQuery.ajax({url:this.url()+"/contents?"+jQuery.param({ids:b.join(",")}),error:function(f,c,d){var e="ERROR updating hdas from api history contents:";a.log(e,b,f,c,d);alert(e+b.join(","))},success:function(d,c,f){a.log(a+".updateHdas, success:",d,c,f);var e=[];_.each(d,function(h,i){var g=a.hdas.get(h.id);if(g){a.log("found existing model in list for id "+h.id+", updating...:");g.set(h)}else{a.log("NO existing model for id "+h.id+", creating...:");e.push(h)}});if(e.length){a.addHdas(e)}}})},addHdas:function(a){var b=this;_.each(a,function(c,d){var e=b.hdas.hidToCollectionIndex(c.hid);c.history_id=b.get("id");b.hdas.add(new HistoryDatasetAssociation(c),{at:e,silent:true})});b.hdas.trigger("add",a)},toString:function(){var a=(this.get("name"))?(","+this.get("name")):("");return"History("+this.get("id")+a+")"}});History.UPDATE_DELAY=4000;var HistoryCollection=Backbone.Collection.extend(LoggableMixin).extend({model:History,urlRoot:"api/histories"}); \ No newline at end of file +var History=BaseModel.extend(LoggableMixin).extend({defaults:{id:"",name:"",state:"",diskSize:0,deleted:false,annotation:null,message:null},urlRoot:"api/histories/",url:function(){return"api/histories/"+this.get("id")},initialize:function(a,b){this.log(this+".initialize:",a,b);this.hdas=new HDACollection();if(b){if(_.isArray(b)){this.hdas.reset(b);this.checkForUpdates()}else{if(_.isString(b)&&(b.match(/error/i))){alert(_l("Error loading bootstrapped history")+":\n"+b)}}}},loadFromApi:function(a,c){var b=this;b.attributes.id=a;jQuery.when(jQuery.ajax("api/users/current"),b.fetch()).then(function(e,d){b.attributes.user=e[0];b.trigger("loaded:user",e[0]);b.trigger("loaded",d[0])}).then(function(){jQuery.ajax(b.url()+"/contents?"+jQuery.param({ids:b.hdaIdsFromStateIds().join(",")})).success(function(d){b.hdas.reset(d);b.checkForUpdates();b.trigger("loaded:hdas",d);if(c){callback(b)}})})},hdaIdsFromStateIds:function(){return _.reduce(_.values(this.get("state_ids")),function(b,a){return b.concat(a)})},checkForUpdates:function(a){if(this.hdas.running().length){this.stateUpdater()}else{this.trigger("ready")}return this},stateUpdater:function(){var c=this,a=this.get("state"),b=this.get("state_ids");jQuery.ajax("api/histories/"+this.get("id")).success(function(d){c.set(d);c.log("current history state:",c.get("state"),"(was)",a,"new size:",c.get("nice_size"));var e=[];_.each(_.keys(d.state_ids),function(g){var f=_.difference(d.state_ids[g],b[g]);e=e.concat(f)});if(e.length){c.fetchHdaUpdates(e)}if((c.get("state")===HistoryDatasetAssociation.STATES.RUNNING)||(c.get("state")===HistoryDatasetAssociation.STATES.QUEUED)){setTimeout(function(){c.stateUpdater()},History.UPDATE_DELAY)}else{c.trigger("ready")}}).error(function(f,d,e){if(!((f.readyState===0)&&(f.status===0))){alert(_l("Error getting history updates from the server.")+"\n"+e)}})},fetchHdaUpdates:function(b){var a=this;jQuery.ajax({url:this.url()+"/contents?"+jQuery.param({ids:b.join(",")}),error:function(h,c,d){if((h.readyState===0)&&(h.status===0)){return}var f=JSON.parse(h.responseText);if(_.isArray(f)){var e=_.groupBy(f,function(i){if(_.has(i,"error")){return"errored"}return"ok"});a.log("fetched, errored datasets:",e.errored);a.updateHdas(f)}else{var g=_l("ERROR updating hdas from api history contents")+": ";a.log(g,b,h,c,d,errorJSON);alert(g+b.join(","))}},success:function(d,c,e){a.log(a+".fetchHdaUpdates, success:",c,e);a.updateHdas(d)}})},updateHdas:function(a){var c=this,b=[];c.log(c+".updateHdas:",a);_.each(a,function(e,f){var d=c.hdas.get(e.id);if(d){c.log("found existing model in list for id "+e.id+", updating...:");d.set(e)}else{c.log("NO existing model for id "+e.id+", creating...:");b.push(e)}});if(b.length){c.addHdas(b)}},addHdas:function(a){var b=this;_.each(a,function(c,d){var e=b.hdas.hidToCollectionIndex(c.hid);c.history_id=b.get("id");b.hdas.add(new HistoryDatasetAssociation(c),{at:e,silent:true})});b.hdas.trigger("add",a)},toString:function(){var a=(this.get("name"))?(","+this.get("name")):("");return"History("+this.get("id")+a+")"}});History.UPDATE_DELAY=4000;var HistoryCollection=Backbone.Collection.extend(LoggableMixin).extend({model:History,urlRoot:"api/histories"}); \ No newline at end of file diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 static/scripts/packed/viz/trackster_ui.js --- a/static/scripts/packed/viz/trackster_ui.js +++ b/static/scripts/packed/viz/trackster_ui.js @@ -1,1 +1,1 @@ -define(["base","libs/underscore","viz/trackster/slotting","viz/trackster/painters","viz/trackster/tracks","viz/visualization"],function(g,c,h,e,b,d){var a=b.object_from_template;var f=g.Base.extend({initialize:function(j){this.baseURL=j},createButtonMenu:function(){var j=this,k=create_icon_buttons_menu([{icon_class:"plus-button",title:"Add tracks",on_click:function(){d.select_datasets(select_datasets_url,add_track_async_url,{"f-dbkey":view.dbkey},function(l){c.each(l,function(m){view.add_drawable(a(m,view,view))})})}},{icon_class:"block--plus",title:"Add group",on_click:function(){view.add_drawable(new b.DrawableGroup(view,view,{name:"New Group"}))}},{icon_class:"bookmarks",title:"Bookmarks",on_click:function(){parent.force_right_panel(($("div#right").css("right")=="0px"?"hide":"show"))}},{icon_class:"globe",title:"Circster",on_click:function(){window.location=j.baseURL+"visualization/circster?id="+view.vis_id}},{icon_class:"disk--arrow",title:"Save",on_click:function(){show_modal("Saving...","progress");var l=[];$(".bookmark").each(function(){l.push({position:$(this).children(".position").text(),annotation:$(this).children(".annotation").text()})});var m=(view.overview_drawable?view.overview_drawable.name:null),n={view:view.to_dict(),viewport:{chrom:view.chrom,start:view.low,end:view.high,overview:m},bookmarks:l};$.ajax({url:galaxy_paths.get("visualization_url"),type:"POST",dataType:"json",data:{id:view.vis_id,title:view.name,dbkey:view.dbkey,type:"trackster",vis_json:JSON.stringify(n)}}).success(function(o){hide_modal();view.vis_id=o.vis_id;view.has_changes=false;window.history.pushState({},"",o.url+window.location.hash)}).error(function(){show_modal("Could Not Save","Could not save visualization. Please try again later.",{Close:hide_modal})})}},{icon_class:"cross-circle",title:"Close",on_click:function(){window.location=j.baseURL+"visualization/list"}}],{tooltip_config:{placement:"bottom"}});this.buttonMenu=k;return k},add_bookmarks:function(){var j=this,k=this.baseURL;show_modal("Select dataset for new bookmarks","progress");$.ajax({url:this.baseURL+"/visualization/list_histories",data:{"f-dbkey":view.dbkey},error:function(){alert("Grid failed")},success:function(l){show_modal("Select dataset for new bookmarks",l,{Cancel:function(){hide_modal()},Insert:function(){$("input[name=id]:checked,input[name=ldda_ids]:checked").first().each(function(){var m,n=$(this).val();if($(this).attr("name")==="id"){m={hda_id:n}}else{m={ldda_id:n}}$.ajax({url:this.baseURL+"/visualization/bookmarks_from_dataset",data:m,dataType:"json"}).then(function(o){for(i=0;i<o.data.length;i++){var p=o.data[i];j.add_bookmark(p[0],p[1])}})});hide_modal()}})}})},add_bookmark:function(n,l,j){var p=$("#bookmarks-container"),r=$("<div/>").addClass("bookmark").appendTo(p);var s=$("<div/>").addClass("position").appendTo(r),o=$("<a href=''/>").text(n).appendTo(s).click(function(){view.go_to(n);return false}),m=$("<div/>").text(l).appendTo(r);if(j){var q=$("<div/>").addClass("delete-icon-container").prependTo(r).click(function(){r.slideUp("fast");r.remove();view.has_changes=true;return false}),k=$("<a href=''/>").addClass("icon-button delete").appendTo(q);m.make_text_editable({num_rows:3,use_textarea:true,help_text:"Edit bookmark note"}).addClass("annotation")}view.has_changes=true;return r},create_visualization:function(o,j,n,p,m){var l=this,k=new b.TracksterView(o);k.editor=true;$.when(k.load_chroms_deferred).then(function(A){if(j){var y=j.chrom,q=j.start,v=j.end,s=j.overview;if(y&&(q!==undefined)&&v){k.change_chrom(y,q,v)}}else{k.change_chrom(A[0].chrom)}if(n){var t,r,u;for(var w=0;w<n.length;w++){k.add_drawable(a(n[w],k,k))}}k.update_intro_div();var z;for(var w=0;w<k.drawables.length;w++){if(k.drawables[w].name===s){k.set_overview(k.drawables[w]);break}}if(p){var x;for(var w=0;w<p.length;w++){x=p[w];l.add_bookmark(x.position,x.annotation,m)}}k.has_changes=false});return k},init_keyboard_nav:function(j){$(document).keydown(function(k){if($(k.srcElement).is(":input")){return}switch(k.which){case 37:j.move_fraction(0.25);break;case 38:var l=Math.round(j.viewport_container.height()/15);j.viewport_container.scrollTop(j.viewport_container.scrollTop()-20);break;case 39:j.move_fraction(-0.25);break;case 40:var l=Math.round(j.viewport_container.height()/15);j.viewport_container.scrollTop(j.viewport_container.scrollTop()+20);break}})}});return{object_from_template:a,TracksterUI:f}}); \ No newline at end of file +define(["base","libs/underscore","viz/trackster/slotting","viz/trackster/painters","viz/trackster/tracks","viz/visualization"],function(g,c,h,e,b,d){var a=b.object_from_template;var f=g.Base.extend({initialize:function(j){this.baseURL=j},createButtonMenu:function(){var j=this,k=create_icon_buttons_menu([{icon_class:"plus-button",title:"Add tracks",on_click:function(){d.select_datasets(select_datasets_url,add_track_async_url,{"f-dbkey":view.dbkey},function(l){c.each(l,function(m){view.add_drawable(a(m,view,view))})})}},{icon_class:"block--plus",title:"Add group",on_click:function(){view.add_drawable(new b.DrawableGroup(view,view,{name:"New Group"}))}},{icon_class:"bookmarks",title:"Bookmarks",on_click:function(){parent.force_right_panel(($("div#right").css("right")=="0px"?"hide":"show"))}},{icon_class:"globe",title:"Circster",on_click:function(){window.location=j.baseURL+"visualization/circster?id="+view.vis_id}},{icon_class:"disk--arrow",title:"Save",on_click:function(){show_modal("Saving...","progress");var l=[];$(".bookmark").each(function(){l.push({position:$(this).children(".position").text(),annotation:$(this).children(".annotation").text()})});var m=(view.overview_drawable?view.overview_drawable.name:null),n={view:view.to_dict(),viewport:{chrom:view.chrom,start:view.low,end:view.high,overview:m},bookmarks:l};$.ajax({url:galaxy_paths.get("visualization_url"),type:"POST",dataType:"json",data:{id:view.vis_id,title:view.name,dbkey:view.dbkey,type:"trackster",vis_json:JSON.stringify(n)}}).success(function(o){hide_modal();view.vis_id=o.vis_id;view.has_changes=false;window.history.pushState({},"",o.url+window.location.hash)}).error(function(){show_modal("Could Not Save","Could not save visualization. Please try again later.",{Close:hide_modal})})}},{icon_class:"cross-circle",title:"Close",on_click:function(){window.location=j.baseURL+"visualization/list"}}],{tooltip_config:{placement:"bottom"}});this.buttonMenu=k;return k},add_bookmarks:function(){var j=this,k=this.baseURL;show_modal("Select dataset for new bookmarks","progress");$.ajax({url:this.baseURL+"/visualization/list_histories",data:{"f-dbkey":view.dbkey},error:function(){alert("Grid failed")},success:function(l){show_modal("Select dataset for new bookmarks",l,{Cancel:function(){hide_modal()},Insert:function(){$("input[name=id]:checked,input[name=ldda_ids]:checked").first().each(function(){var m,n=$(this).val();if($(this).attr("name")==="id"){m={hda_id:n}}else{m={ldda_id:n}}$.ajax({url:this.baseURL+"/visualization/bookmarks_from_dataset",data:m,dataType:"json"}).then(function(o){for(i=0;i<o.data.length;i++){var p=o.data[i];j.add_bookmark(p[0],p[1])}})});hide_modal()}})}})},add_bookmark:function(n,l,j){var p=$("#bookmarks-container"),r=$("<div/>").addClass("bookmark").appendTo(p);var s=$("<div/>").addClass("position").appendTo(r),o=$("<a href=''/>").text(n).appendTo(s).click(function(){view.go_to(n);return false}),m=$("<div/>").text(l).appendTo(r);if(j){var q=$("<div/>").addClass("delete-icon-container").prependTo(r).click(function(){r.slideUp("fast");r.remove();view.has_changes=true;return false}),k=$("<a href=''/>").addClass("icon-button delete").appendTo(q);m.make_text_editable({num_rows:3,use_textarea:true,help_text:"Edit bookmark note"}).addClass("annotation")}view.has_changes=true;return r},create_visualization:function(o,j,n,p,m){var l=this,k=new b.TracksterView(o);k.editor=true;$.when(k.load_chroms_deferred).then(function(A){if(j){var y=j.chrom,q=j.start,v=j.end,s=j.overview;if(y&&(q!==undefined)&&v){k.change_chrom(y,q,v)}else{k.change_chrom(A[0].chrom)}}else{k.change_chrom(A[0].chrom)}if(n){var t,r,u;for(var w=0;w<n.length;w++){k.add_drawable(a(n[w],k,k))}}k.update_intro_div();var z;for(var w=0;w<k.drawables.length;w++){if(k.drawables[w].name===s){k.set_overview(k.drawables[w]);break}}if(p){var x;for(var w=0;w<p.length;w++){x=p[w];l.add_bookmark(x.position,x.annotation,m)}}k.has_changes=false});return k},init_keyboard_nav:function(j){$(document).keydown(function(k){if($(k.srcElement).is(":input")){return}switch(k.which){case 37:j.move_fraction(0.25);break;case 38:var l=Math.round(j.viewport_container.height()/15);j.viewport_container.scrollTop(j.viewport_container.scrollTop()-20);break;case 39:j.move_fraction(-0.25);break;case 40:var l=Math.round(j.viewport_container.height()/15);j.viewport_container.scrollTop(j.viewport_container.scrollTop()+20);break}})}});return{object_from_template:a,TracksterUI:f}}); \ No newline at end of file diff -r d4d5588574ccb7faea8abfb0f0ca9fe9b48e701e -r 149f0fc73fae0494fa5cf29ec719bf38981c01b6 templates/grid_base.mako --- a/templates/grid_base.mako +++ b/templates/grid_base.mako @@ -52,23 +52,8 @@ </%def><%def name="grid_javascripts()"> - ${h.js("libs/jquery/jquery.autocomplete", "galaxy.autocom_tagging", "libs/jquery/jquery.rating" )} + ${h.js("libs/jquery/jquery.autocomplete", "galaxy.autocom_tagging", "libs/jquery/jquery.rating", "galaxy.grids" )} <script type="text/javascript"> - // This is necessary so that, when nested arrays are used in ajax/post/get methods, square brackets ('[]') are - // not appended to the identifier of a nested array. - jQuery.ajaxSettings.traditional = true; - - ## TODO: generalize and move into galaxy.base.js - $(document).ready(function() { - init_grid_elements(); - init_grid_controls(); - - // Initialize text filters to select text on click and use normal font when user is typing. - $('input[type=text]').each(function() { - $(this).click(function() { $(this).select(); } ) - .keyup(function () { $(this).css("font-style", "normal"); }) - }); - }); ## TODO: Can this be moved into base.mako? Also, this is history-specific grid code. %if refresh_frames: %if 'masthead' in refresh_frames: @@ -90,7 +75,7 @@ } else { // TODO: redirecting to root should be done on the server side so that page - // doesn't have to load. + // does not have to load. // No history frame, so refresh to root to see history. window.top.location.href = "${h.url_for( controller='root' )}"; @@ -105,146 +90,21 @@ } %endif %endif - + + // Needed URLs for grid history searching. + var history_tag_autocomplete_url = "${h.url_for( controller='tag', action='tag_autocomplete_data', item_class='History' )}", + history_name_autocomplete_url = "${h.url_for( controller='history', action='name_autocomplete_data' )}"; + // - // Code to handle grid operations: filtering, sorting, paging, and operations. + // Create grid object. // - + // Operations that are async (AJAX) compatible. - var async_ops = {}; + var async_ops = []; %for operation in [op for op in grid.operations if op.async_compatible]: - async_ops['${operation.label.lower()}'] = "True"; + async_ops.push('${operation.label.lower()}'); %endfor - - // Init operation buttons. - function init_operation_buttons() { - // Initialize operation buttons. - $('input[name=operation]:submit').each(function() { - $(this).click( function() { - var webapp = $("input[name=webapp]").attr("value"); - var operation_name = $(this).val(); - // For some reason, $('input[name=id]:checked').val() does not return all ids for checked boxes. - // The code below performs this function. - var item_ids = []; - $('input[name=id]:checked').each(function() { - item_ids.push( $(this).val() ); - }); - do_operation(webapp, operation_name, item_ids); - }); - }); - }; - - // Initialize grid controls - function init_grid_controls() { - init_operation_buttons(); - - // Initialize submit image elements. - $('.submit-image').each( function() { - // On mousedown, add class to simulate click. - $(this).mousedown( function() { - $(this).addClass('gray-background'); - }); - - // On mouseup, add class to simulate click. - $(this).mouseup( function() { - $(this).removeClass('gray-background'); - }); - }); - - // Initialize sort links. - $('.sort-link').each( function() { - $(this).click( function() { - set_sort_condition( $(this).attr('sort_key') ); - return false; - }); - }); - - // Initialize page links. - $('.page-link > a').each( function() { - $(this).click( function() { - set_page( $(this).attr('page_num') ); - return false; - }); - }); - // Initialize categorical filters. - $('.categorical-filter > a').each( function() { - $(this).click( function() { - set_categorical_filter( $(this).attr('filter_key'), $(this).attr('filter_val') ); - return false; - }); - }); - - // Initialize text filters. - $('.text-filter-form').each( function() { - $(this).submit( function() { - var column_key = $(this).attr('column_key'); - var text_input_obj = $('#input-' + column_key + '-filter'); - var text_input = text_input_obj.val(); - text_input_obj.val(''); - add_filter_condition(column_key, text_input, true); - return false; - }); - }); - - // Initialize autocomplete for text inputs in search UI. - var t = $("#input-tags-filter"); - if (t.length) { - t.autocomplete( "${h.url_for( controller='tag', action='tag_autocomplete_data', item_class='History' )}", - { selectFirst: false, autoFill: false, highlight: false, mustMatch: false }); - } - - var t2 = $("#input-name-filter"); - if (t2.length) { - t2.autocomplete( "${h.url_for( controller='history', action='name_autocomplete_data' )}", - { selectFirst: false, autoFill: false, highlight: false, mustMatch: false }); - } - - // Initialize standard, advanced search toggles. - $('.advanced-search-toggle').each( function() { - $(this).click( function() { - $("#standard-search").slideToggle('fast'); - $('#advanced-search').slideToggle('fast'); - return false; - }); - }); - } - - // Initialize grid elements. - function init_grid_elements() { - // Initialize grid selection checkboxes. - $(".grid").each( function() { - var checkboxes = $(this).find("input.grid-row-select-checkbox"); - var check_count = $(this).find("span.grid-selected-count"); - var update_checked = function() { - check_count.text( $(checkboxes).filter(":checked").length ); - }; - - $(checkboxes).each( function() { - $(this).change(update_checked); - }); - update_checked(); - }); - - // Initialize item labels. - $(".label").each( function() { - // If href has an operation in it, do operation when clicked. Otherwise do nothing. - var href = $(this).attr('href'); - if ( href !== undefined && href.indexOf('operation=') != -1 ) { - $(this).click( function() { - do_operation_from_href( $(this).attr('href') ); - return false; - }); - } - }); - - // Initialize ratings. - $('.community_rating_star').rating({}); - - // Initialize item menu operations. - make_popup_menus(); - } - // Filter values for categorical filters. var categorical_filters = {}; %for column in grid.columns: @@ -253,367 +113,22 @@ categorical_filters['${column.key}'] = ${column.key}_filters; %endif %endfor - - // Initialize URL args with filter arguments. - var url_args_init = ${h.to_json_string( cur_filter_dict )}, - url_args = {}; - - // Place "f-" in front of all filter arguments. - - for (arg in url_args_init) { - url_args["f-" + arg] = url_args_init[arg]; - } - - // Add sort argument to URL args. - url_args['sort'] = "${sort_key}"; - - // Add show_item_checkboxes argument to URL args. - url_args['show_item_checkboxes'] = ("${context.get('show_item_checkboxes', False)}" === "True"); - - // Add async keyword to URL args. - url_args['async'] = true; - - // Add page to URL args. - url_args['page'] = ${cur_page_num}; - - var num_pages = ${num_pages}; - - // Go back to page one; this is useful when a filter is applied. - function go_page_one() { - // Need to go back to page 1 if not showing all. - var cur_page = url_args['page']; - if (cur_page !== null && cur_page !== undefined && cur_page != 'all') { - url_args['page'] = 1; - } - } - - // Add a condition to the grid filter; this adds the condition and refreshes the grid. - function add_filter_condition(name, value, append) { - // Do nothing is value is empty. - if (value == "") { - return false; - } - - // Update URL arg with new condition. - if (append) { - // Update or append value. - var cur_val = url_args["f-" + name]; - var new_val; - if (cur_val === null || cur_val === undefined) { - new_val = value; - } else if (typeof(cur_val) == "string") { - if (cur_val == "All") { - new_val = value; - } else { - // Replace string with array. - var values = []; - values[0] = cur_val; - values[1] = value; - new_val = values; - } - } else { - // Current value is an array. - new_val = cur_val; - new_val[new_val.length] = value; - } - url_args["f-" + name] = new_val; - } else { - // Replace value. - url_args["f-" + name] = value; - } - - // Add button that displays filter and provides a button to delete it. - var t = $("<span>" + value + "<a href='javascript:void(0);'><span class='delete-search-icon' /></a></span>"); - t.addClass('text-filter-val'); - t.click(function() { - // Remove filter condition. - - // Remove visible element. - $(this).remove(); - - // Remove condition from URL args. - var cur_val = url_args["f-" + name]; - if (cur_val === null || cur_val === undefined) { - // Unexpected. Throw error? - } else if (typeof(cur_val) == "string") { - if (cur_val == "All") { - // Unexpected. Throw error? - } else { - // Remove condition. - delete url_args["f-" + name]; - } - } else { - // Current value is an array. - var conditions = cur_val; - for (var index = 0; index < conditions.length; index++) { - if (conditions[index] == value) { - conditions.splice(index, 1); - break; - } - } - } - - go_page_one(); - update_grid(); - }); - - var container = $('#' + name + "-filtering-criteria"); - container.append(t); - - go_page_one(); - update_grid(); - } - - // Add tag to grid filter. - function add_tag_to_grid_filter(tag_name, tag_value) { - // Put tag name and value together. - var tag = tag_name + (tag_value !== undefined && tag_value != "" ? ":" + tag_value : ""); - $('#advanced-search').show('fast'); - add_filter_condition("tags", tag, true); - } - - // Set sort condition for grid. - function set_sort_condition(col_key) { - // Set new sort condition. New sort is col_key if sorting new column; if reversing sort on - // currently sorted column, sort is reversed. - var cur_sort = url_args['sort']; - var new_sort = col_key; - if ( cur_sort.indexOf( col_key ) != -1) { - // Reverse sort. - if ( cur_sort.substring(0,1) != '-' ) { - new_sort = '-' + col_key; - } else { - // Sort reversed by using just col_key. - } - } - - // Remove sort arrows elements. - $('.sort-arrow').remove(); - - // Add sort arrow element to new sort column. - var sort_arrow = (new_sort.substring(0,1) == '-') ? "↑" : "↓"; - var t = $("<span>" + sort_arrow + "</span>").addClass('sort-arrow'); - var th = $("#" + col_key + '-header'); - th.append(t); - - // Need to go back to page 1 if not showing all. - var cur_page = url_args['page']; - if (cur_page !== null && cur_page !== undefined && cur_page != 'all') { - url_args['page'] = 1; - } - // Update grid. - url_args['sort'] = new_sort; - go_page_one(); - update_grid(); - } - - // Set new value for categorical filter. - function set_categorical_filter(name, new_value) { - // Update filter hyperlinks to reflect new filter value. - var category_filter = categorical_filters[name]; - var cur_value = url_args["f-" + name]; - $("." + name + "-filter").each( function() { - var text = $.trim( $(this).text() ); - var filter = category_filter[text]; - var filter_value = filter[name]; - if (filter_value == new_value) { - // Remove filter link since grid will be using this filter. It is assumed that - // this element has a single child, a hyperlink/anchor with text. - $(this).empty(); - $(this).addClass("current-filter"); - $(this).append(text); - } else if (filter_value == cur_value) { - // Add hyperlink for this filter since grid will no longer be using this filter. It is assumed that - // this element has a single child, a hyperlink/anchor. - $(this).empty(); - var t = $("<a href='#'>" + text + "</a>"); - t.click(function() { - set_categorical_filter( name, filter_value ); - }); - $(this).removeClass("current-filter"); - $(this).append(t); - } - }); - - // Update grid. - url_args["f-" + name] = new_value; - go_page_one(); - update_grid(); - } - - // Set page to view. - function set_page(new_page) { - // Update page hyperlink to reflect new page. - $(".page-link").each( function() { - var id = $(this).attr('id'); - var page_num = parseInt( id.split("-")[2] ); // Id has form 'page-link-<page_num> - var cur_page = url_args['page']; - if (page_num == new_page) { - // Remove link to page since grid will be on this page. It is assumed that - // this element has a single child, a hyperlink/anchor with text. - var text = $(this).children().text(); - $(this).empty(); - $(this).addClass("inactive-link"); - $(this).text(text); - } else if (page_num == cur_page) { - // Add hyperlink to this page since grid will no longer be on this page. It is assumed that - // this element has a single child, a hyperlink/anchor. - var text = $(this).text(); - $(this).empty(); - $(this).removeClass("inactive-link"); - var t = $("<a href='#'>" + text + "</a>"); - t.click(function() { - set_page(page_num); - }); - $(this).append(t); - } - }); - - var maintain_page_links = true; - if (new_page == "all") { - url_args['page'] = new_page; - maintain_page_links = false; - } else { - url_args['page'] = parseInt(new_page); - } - update_grid(maintain_page_links); - } - - // Perform a grid operation. - function do_operation(webapp, operation, item_ids) { - operation = operation.toLowerCase(); - - // Update URL args. - url_args["webapp"] = webapp; - url_args["operation"] = operation; - url_args["id"] = item_ids; - - // If operation cannot be performed asynchronously, redirect to location. Otherwise do operation. - var no_async = ( async_ops[operation] === undefined || async_ops[operation] === null); - if (no_async) { - go_to_URL(); - } else { - update_grid(true); - delete url_args['webapp']; - delete url_args['operation']; - delete url_args['id']; - } - } - - // Perform a hyperlink click that initiates an operation. If there is no operation, ignore click. - function do_operation_from_href(href) { - // Get operation, id in hyperlink's href. - var href_parts = href.split("?"); - if (href_parts.length > 1) { - var href_parms_str = href_parts[1]; - var href_parms = href_parms_str.split("&"); - var operation = null; - var id = -1; - var webapp = 'galaxy'; - for (var index = 0; index < href_parms.length; index++) { - if (href_parms[index].indexOf('operation') != -1) { - // Found operation parm; get operation value. - operation = href_parms[index].split('=')[1]; - } else if (href_parms[index].indexOf('id') != -1) { - // Found id parm; get id value. - id = href_parms[index].split('=')[1]; - } else if (href_parms[index].indexOf('webapp') != -1) { - // Found webapp parm; get webapp value. - webapp = href_parms[index].split('=')[1]; - } - } - // Do operation. - do_operation(webapp, operation, id); - return false; - } - } - - // Navigate window to the URL defined by url_args. This method should be used to short-circuit grid AJAXing. - function go_to_URL() { - // Not async request. - url_args['async'] = false; - - // Build argument string. - var arg_str = ""; - for (var arg in url_args) { - arg_str = arg_str + arg + "=" + url_args[arg] + "&"; - } - - // Go. - window.location = encodeURI( "${h.url_for()}?" + arg_str ); - } - - // Update grid. - function update_grid(maintain_page_links) { - ## If grid is not using async, then go to URL. - %if not grid.use_async: - go_to_URL(); - return; - %endif - - // If there's an operation in the args, do POST; otherwise, do GET. - var operation = url_args['operation']; - var method = (operation !== null && operation !== undefined ? "POST" : "GET" ); - $('.loading-elt-overlay').show(); // Show overlay to indicate loading and prevent user actions. - $.ajax({ - type: method, - url: "${h.url_for()}", - data: url_args, - error: function() { alert( "Grid refresh failed" ); }, - success: function(response_text) { - // HACK: use a simple string to separate the elements in the - // response: (1) table body; (2) number of pages in table; and (3) message. - var parsed_response_text = response_text.split("*****"); - - // Update grid body and footer. - $('#grid-table-body').html(parsed_response_text[0]); - // FIXME: this does not work at all; what's needed is a function - // that updates page links when number of pages changes. - $('#grid-table-footer').html(parsed_response_text[1]); - - // Trigger custom event to indicate grid body has changed. - $('#grid-table-body').trigger('update'); - - // Init grid. - init_grid_elements(); - init_operation_buttons(); - make_popup_menus(); - - // Hide loading overlay. - $('.loading-elt-overlay').hide(); - - // Show message if there is one. - var message = $.trim( parsed_response_text[2] ); - if (message != "") { - $('#grid-message').html( message ).show(); - setTimeout( function() { $('#grid-message').hide(); }, 5000); - } - } - }); - } - - function check_all_items() { - var chk_all = document.getElementById('check_all'); - var checks = document.getElementsByTagName('input'); - //var boxLength = checks.length; - var total = 0; - if ( chk_all.checked == true ) { - for ( i=0; i < checks.length; i++ ) { - if ( checks[i].name.indexOf( 'id' ) != -1) { - checks[i].checked = true; - total++; - } - } - } - else { - for ( i=0; i < checks.length; i++ ) { - if ( checks[i].name.indexOf( 'id' ) != -1) { - checks[i].checked = false - } - } - } - init_grid_elements(); - } + + /** Returns true if string denotes true. */ + var is_true = function(s) { return _.indexOf(['True', 'true', 't'], s) !== -1; }; + + // Create grid. + var grid = new Grid({ + url_base: '${h.url_for()}', + async: is_true('${grid.use_async}'), + async_ops: async_ops, + categorical_filters: categorical_filters, + filters: ${h.to_json_string( cur_filter_dict )}, + sort_key: '${sort_key}', + show_item_checkboxes: is_true('${context.get('show_item_checkboxes', False)}'), + cur_page: ${cur_page_num}, + num_pages: ${num_pages} + }); </script></%def> @@ -700,7 +215,6 @@ show_item_checkboxes = True %><form action="${url()}" method="post" onsubmit="return false;"> - <input type="hidden" name="webapp" value="${webapp}"/><table id="grid-table" class="grid"><thead id="grid-table-header"><tr> 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.