galaxy-commits
Threads by month
- ----- 2026 -----
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2025 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2010 -----
- December
- November
- October
- September
- August
- July
- June
- May
- 15302 discussions
11 new commits in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/320ae026f73a/
Changeset: 320ae026f73a
Branch: search
User: Kyle Ellrott
Date: 2013-06-21 22:31:02
Summary: Adding 'state' field to the jobn search view. Also adding '!=' compatitor to GQL
Affected #: 2 files
diff -r fd3a82d33bb6896ba6395a5e83add5c6ac7f7fbf -r 320ae026f73a849c77a580410a5a3d6927ef1b91 lib/galaxy/model/__init__.py
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -158,8 +158,8 @@
class Job( object, APIItem ):
- api_collection_visible_keys = [ 'id' ]
- api_element_visible_keys = [ 'id' ]
+ api_collection_visible_keys = [ 'id', 'state' ]
+ api_element_visible_keys = [ 'id', 'state' ]
"""
A job represents a request to run a tool given input datasets, tool
diff -r fd3a82d33bb6896ba6395a5e83add5c6ac7f7fbf -r 320ae026f73a849c77a580410a5a3d6927ef1b91 lib/galaxy/model/search.py
--- a/lib/galaxy/model/search.py
+++ b/lib/galaxy/model/search.py
@@ -107,6 +107,8 @@
if operator == "=":
#print field.sqlalchemy_field == right, field.sqlalchemy_field, right
self.query = self.query.filter( field.sqlalchemy_field == right )
+ elif operator == "!=":
+ self.query = self.query.filter( field.sqlalchemy_field != right )
elif operator == "like":
self.query = self.query.filter( field.sqlalchemy_field.like(right) )
else:
@@ -433,6 +435,7 @@
DOMAIN = "job"
FIELDS = {
'tool_name' : ViewField('tool_name', sqlalchemy_field=Job.tool_id),
+ 'state' : ViewField('state', sqlalchemy_field=Job.state),
'param' : ViewField('param', handler=job_param_filter),
'input_hda' : ViewField('input_hda', handler=job_input_hda_filter, id_decode=True),
'output_hda' : ViewField('output_hda', handler=job_output_hda_filter, id_decode=True)
@@ -499,6 +502,7 @@
comparison = ( '=' -> '='
| '>' -> '>'
| '<' -> '<'
+ | '!=' -> '!='
| '>=' -> '>='
| '<=' -> '<='
| 'like' -> 'like'
https://bitbucket.org/galaxy/galaxy-central/commits/460c7dc52f92/
Changeset: 460c7dc52f92
Branch: search
User: Kyle Ellrott
Date: 2013-06-27 20:59:24
Summary: Default merge
Affected #: 197 files
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/binary.py
--- a/lib/galaxy/datatypes/binary.py
+++ b/lib/galaxy/datatypes/binary.py
@@ -267,25 +267,25 @@
# bam does not use '#' to indicate comments/headers - we need to strip out those headers from the std. providers
#TODO:?? seems like there should be an easier way to do/inherit this - metadata.comment_char?
#TODO: incorporate samtools options to control output: regions first, then flags, etc.
- @dataproviders.decorators.dataprovider_factory( 'line' )
+ @dataproviders.decorators.dataprovider_factory( 'line', dataproviders.line.FilteredLineDataProvider.settings )
def line_dataprovider( self, dataset, **settings ):
samtools_source = dataproviders.dataset.SamtoolsDataProvider( dataset )
settings[ 'comment_char' ] = '@'
return dataproviders.line.FilteredLineDataProvider( samtools_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'regex-line' )
+ @dataproviders.decorators.dataprovider_factory( 'regex-line', dataproviders.line.RegexLineDataProvider.settings )
def regex_line_dataprovider( self, dataset, **settings ):
samtools_source = dataproviders.dataset.SamtoolsDataProvider( dataset )
settings[ 'comment_char' ] = '@'
return dataproviders.line.RegexLineDataProvider( samtools_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'column' )
+ @dataproviders.decorators.dataprovider_factory( 'column', dataproviders.column.ColumnarDataProvider.settings )
def column_dataprovider( self, dataset, **settings ):
samtools_source = dataproviders.dataset.SamtoolsDataProvider( dataset )
settings[ 'comment_char' ] = '@'
return dataproviders.column.ColumnarDataProvider( samtools_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'map' )
+ @dataproviders.decorators.dataprovider_factory( 'map', dataproviders.column.MapDataProvider.settings )
def map_dataprovider( self, dataset, **settings ):
samtools_source = dataproviders.dataset.SamtoolsDataProvider( dataset )
settings[ 'comment_char' ] = '@'
@@ -293,30 +293,30 @@
# these can't be used directly - may need BamColumn, BamMap (Bam metadata -> column/map)
# OR - see genomic_region_dataprovider
- #(a)dataproviders.decorators.dataprovider_factory( 'dataset-column' )
+ #(a)dataproviders.decorators.dataprovider_factory( 'dataset-column', dataproviders.column.ColumnarDataProvider.settings )
#def dataset_column_dataprovider( self, dataset, **settings ):
# settings[ 'comment_char' ] = '@'
# return super( Sam, self ).dataset_column_dataprovider( dataset, **settings )
- #(a)dataproviders.decorators.dataprovider_factory( 'dataset-map' )
+ #(a)dataproviders.decorators.dataprovider_factory( 'dataset-map', dataproviders.column.MapDataProvider.settings )
#def dataset_map_dataprovider( self, dataset, **settings ):
# settings[ 'comment_char' ] = '@'
# return super( Sam, self ).dataset_map_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'header' )
+ @dataproviders.decorators.dataprovider_factory( 'header', dataproviders.line.RegexLineDataProvider.settings )
def header_dataprovider( self, dataset, **settings ):
# in this case we can use an option of samtools view to provide just what we need (w/o regex)
samtools_source = dataproviders.dataset.SamtoolsDataProvider( dataset, '-H' )
return dataproviders.line.RegexLineDataProvider( samtools_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'id-seq-qual' )
+ @dataproviders.decorators.dataprovider_factory( 'id-seq-qual', dataproviders.column.MapDataProvider.settings )
def id_seq_qual_dataprovider( self, dataset, **settings ):
settings[ 'indeces' ] = [ 0, 9, 10 ]
settings[ 'column_types' ] = [ 'str', 'str', 'str' ]
settings[ 'column_names' ] = [ 'id', 'seq', 'qual' ]
return self.map_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region', dataproviders.column.ColumnarDataProvider.settings )
def genomic_region_dataprovider( self, dataset, **settings ):
# GenomicRegionDataProvider currently requires a dataset as source - may not be necc.
#TODO:?? consider (at least) the possible use of a kwarg: metadata_source (def. to source.dataset),
@@ -330,7 +330,7 @@
settings[ 'column_types' ] = [ 'str', 'int', 'int' ]
return self.column_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region-map' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region-map', dataproviders.column.MapDataProvider.settings )
def genomic_region_map_dataprovider( self, dataset, **settings ):
settings[ 'indeces' ] = [ 2, 3, 3 ]
settings[ 'column_types' ] = [ 'str', 'int', 'int' ]
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/converters/bam_to_bigwig_converter.xml
--- a/lib/galaxy/datatypes/converters/bam_to_bigwig_converter.xml
+++ b/lib/galaxy/datatypes/converters/bam_to_bigwig_converter.xml
@@ -1,5 +1,9 @@
<tool id="CONVERTER_bam_to_bigwig_0" name="Convert BAM to BigWig" version="1.0.0" hidden="true"><!-- <description>__NOT_USED_CURRENTLY_FOR_CONVERTERS__</description> -->
+ <requirements>
+ <requirement type="package">ucsc_tools</requirement>
+ <requirement type="package">bedtools</requirement>
+ </requirements><command>
bedtools genomecov -bg -split -ibam $input -g $chromInfo
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/converters/bed_gff_or_vcf_to_bigwig_converter.xml
--- a/lib/galaxy/datatypes/converters/bed_gff_or_vcf_to_bigwig_converter.xml
+++ b/lib/galaxy/datatypes/converters/bed_gff_or_vcf_to_bigwig_converter.xml
@@ -1,5 +1,9 @@
<tool id="CONVERTER_bed_gff_or_vcf_to_bigwig_0" name="Convert BED, GFF, or VCF to BigWig" version="1.0.0" hidden="true"><!-- <description>__NOT_USED_CURRENTLY_FOR_CONVERTERS__</description> -->
+ <requirements>
+ <requirement type="package">ucsc_tools</requirement>
+ <requirement type="package">bedtools</requirement>
+ </requirements><command>
## Remove comments and sort by chromosome.
grep -v '^#' $input | sort -k1,1 |
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/converters/interval_to_bigwig_converter.xml
--- a/lib/galaxy/datatypes/converters/interval_to_bigwig_converter.xml
+++ b/lib/galaxy/datatypes/converters/interval_to_bigwig_converter.xml
@@ -1,6 +1,10 @@
<tool id="CONVERTER_interval_to_bigwig_0" name="Convert Genomic Intervals To Coverage"><!-- <description>__NOT_USED_CURRENTLY_FOR_CONVERTERS__</description> --><!-- Used on the metadata edit page. -->
+ <requirements>
+ <requirement type="package">ucsc_tools</requirement>
+ <requirement type="package">bedtools</requirement>
+ </requirements><command>
## Remove comments and sort by chromosome.
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/converters/sam_to_bigwig_converter.xml
--- a/lib/galaxy/datatypes/converters/sam_to_bigwig_converter.xml
+++ b/lib/galaxy/datatypes/converters/sam_to_bigwig_converter.xml
@@ -1,4 +1,9 @@
<tool id="CONVERTER_sam_to_bigwig_0" name="Convert SAM to BigWig" version="1.0.0" hidden="true">
+ <requirements>
+ <requirement type="package">ucsc_tools</requirement>
+ <requirement type="package">samtools</requirement>
+ <requirement type="package">bedtools</requirement>
+ </requirements><command>
samtools view -bh $input | bedtools genomecov -bg -split -ibam stdin -g $chromInfo
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/data.py
--- a/lib/galaxy/datatypes/data.py
+++ b/lib/galaxy/datatypes/data.py
@@ -593,7 +593,6 @@
Base dataprovider factory for all datatypes that returns the proper provider
for the given `data_format` or raises a `NoProviderAvailable`.
"""
- #TODO:?? is this handling super class providers?
if self.has_dataprovider( data_format ):
return self.dataproviders[ data_format ]( self, dataset, **settings )
raise dataproviders.exceptions.NoProviderAvailable( self, data_format )
@@ -603,12 +602,12 @@
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
return dataproviders.base.DataProvider( dataset_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'chunk' )
+ @dataproviders.decorators.dataprovider_factory( 'chunk', dataproviders.chunk.ChunkDataProvider.settings )
def chunk_dataprovider( self, dataset, **settings ):
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
return dataproviders.chunk.ChunkDataProvider( dataset_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'chunk64' )
+ @dataproviders.decorators.dataprovider_factory( 'chunk64', dataproviders.chunk.Base64ChunkDataProvider.settings )
def chunk64_dataprovider( self, dataset, **settings ):
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
return dataproviders.chunk.Base64ChunkDataProvider( dataset_source, **settings )
@@ -785,7 +784,7 @@
split = classmethod(split)
# ------------- Dataproviders
- @dataproviders.decorators.dataprovider_factory( 'line' )
+ @dataproviders.decorators.dataprovider_factory( 'line', dataproviders.line.FilteredLineDataProvider.settings )
def line_dataprovider( self, dataset, **settings ):
"""
Returns an iterator over the dataset's lines (that have been `strip`ed)
@@ -794,7 +793,7 @@
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
return dataproviders.line.FilteredLineDataProvider( dataset_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'regex-line' )
+ @dataproviders.decorators.dataprovider_factory( 'regex-line', dataproviders.line.RegexLineDataProvider.settings )
def regex_line_dataprovider( self, dataset, **settings ):
"""
Returns an iterator over the dataset's lines
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/dataproviders/base.py
--- a/lib/galaxy/datatypes/dataproviders/base.py
+++ b/lib/galaxy/datatypes/dataproviders/base.py
@@ -22,8 +22,13 @@
icorporate existing visualization/dataproviders
some of the sources (esp. in datasets) don't need to be re-created
+YAGNI: InterleavingMultiSourceDataProvider, CombiningMultiSourceDataProvider
-YAGNI: InterleavingMultiSourceDataProvider, CombiningMultiSourceDataProvider
+datasets API entry point:
+ kwargs should be parsed from strings 2 layers up (in the DatasetsAPI) - that's the 'proper' place for that.
+ but how would it know how/what to parse if it doesn't have access to the classes used in the provider?
+ Building a giant list by sweeping all possible dprov classes doesn't make sense
+ For now - I'm burying them in the class __init__s - but I don't like that
"""
import logging
@@ -31,6 +36,31 @@
# ----------------------------------------------------------------------------- base classes
+class HasSettings( type ):
+ """
+ Metaclass for data providers that allows defining and inheriting
+ a dictionary named 'settings'.
+
+ Useful for allowing class level access to expected variable types
+ passed to class `__init__` functions so they can be parsed from a query string.
+ """
+ # yeah - this is all too acrobatic
+ def __new__( cls, name, base_classes, attributes ):
+ settings = {}
+ # get settings defined in base classes
+ for base_class in base_classes:
+ base_settings = getattr( base_class, 'settings', None )
+ if base_settings:
+ settings.update( base_settings )
+ # get settings defined in this class
+ new_settings = attributes.pop( 'settings', None )
+ if new_settings:
+ settings.update( new_settings )
+ attributes[ 'settings' ] = settings
+ return type.__new__( cls, name, base_classes, attributes )
+
+
+# ----------------------------------------------------------------------------- base classes
class DataProvider( object ):
"""
Base class for all data providers. Data providers:
@@ -39,6 +69,12 @@
(c) do not allow write methods
(but otherwise implement the other file object interface methods)
"""
+ # a definition of expected types for keyword arguments sent to __init__
+ # useful for controlling how query string dictionaries can be parsed into correct types for __init__
+ # empty in this base class
+ __metaclass__ = HasSettings
+ settings = {}
+
def __init__( self, source, **kwargs ):
"""
:param source: the source that this iterator will loop over.
@@ -130,13 +166,16 @@
- `num_valid_data_read`: how many data have been returned from `filter`.
- `num_data_returned`: how many data has this provider yielded.
"""
+ # not useful here - we don't want functions over the query string
+ #settings.update({ 'filter_fn': 'function' })
+
def __init__( self, source, filter_fn=None, **kwargs ):
"""
:param filter_fn: a lambda or function that will be passed a datum and
return either the (optionally modified) datum or None.
"""
super( FilteredDataProvider, self ).__init__( source, **kwargs )
- self.filter_fn = filter_fn
+ self.filter_fn = filter_fn if hasattr( filter_fn, '__call__' ) else None
# count how many data we got from the source
self.num_data_read = 0
# how many valid data have we gotten from the source
@@ -179,6 +218,12 @@
Useful for grabbing sections from a source (e.g. pagination).
"""
+ # define the expected types of these __init__ arguments so they can be parsed out from query strings
+ settings = {
+ 'limit' : 'int',
+ 'offset': 'int'
+ }
+
#TODO: may want to squash this into DataProvider
def __init__( self, source, offset=0, limit=None, **kwargs ):
"""
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/dataproviders/chunk.py
--- a/lib/galaxy/datatypes/dataproviders/chunk.py
+++ b/lib/galaxy/datatypes/dataproviders/chunk.py
@@ -26,6 +26,10 @@
"""
MAX_CHUNK_SIZE = 2**16
DEFAULT_CHUNK_SIZE = MAX_CHUNK_SIZE
+ settings = {
+ 'chunk_index' : 'int',
+ 'chunk_size' : 'int'
+ }
#TODO: subclass from LimitedOffsetDataProvider?
# see web/framework/base.iterate_file, util/__init__.file_reader, and datatypes.tabular
@@ -38,8 +42,8 @@
(gen. in bytes).
"""
super( ChunkDataProvider, self ).__init__( source, **kwargs )
- self.chunk_size = chunk_size
- self.chunk_pos = chunk_index * self.chunk_size
+ self.chunk_size = int( chunk_size )
+ self.chunk_pos = int( chunk_index ) * self.chunk_size
def validate_source( self, source ):
"""
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/dataproviders/column.py
--- a/lib/galaxy/datatypes/dataproviders/column.py
+++ b/lib/galaxy/datatypes/dataproviders/column.py
@@ -29,6 +29,14 @@
the same number of columns as the number of indeces asked for (even if they
are filled with None).
"""
+ settings = {
+ 'indeces' : 'list:int',
+ 'column_count' : 'int',
+ 'column_types' : 'list:str',
+ 'parse_columns' : 'bool',
+ 'deliminator' : 'str'
+ }
+
def __init__( self, source, indeces=None,
column_count=None, column_types=None, parsers=None, parse_columns=True,
deliminator='\t', **kwargs ):
@@ -91,11 +99,11 @@
# how/whether to parse each column value
self.parsers = {}
if parse_columns:
- self.parsers = self._get_default_parsers()
+ self.parsers = self.get_default_parsers()
# overwrite with user desired parsers
self.parsers.update( parsers or {} )
- def _get_default_parsers( self ):
+ def get_default_parsers( self ):
"""
Return parser dictionary keyed for each columnar type
(as defined in datatypes).
@@ -132,7 +140,7 @@
#'gffstrand': # -, +, ?, or '.' for None, etc.
}
- def _parse_value( self, val, type ):
+ def parse_value( self, val, type ):
"""
Attempt to parse and return the given value based on the given type.
@@ -153,7 +161,7 @@
return None
return val
- def _get_column_type( self, index ):
+ def get_column_type( self, index ):
"""
Get the column type for the parser from `self.column_types` or `None`
if the type is unavailable.
@@ -165,18 +173,18 @@
except IndexError, ind_err:
return None
- def _parse_column_at_index( self, columns, parser_index, index ):
+ def parse_column_at_index( self, columns, parser_index, index ):
"""
Get the column type for the parser from `self.column_types` or `None`
if the type is unavailable.
"""
try:
- return self._parse_value( columns[ index ], self._get_column_type( parser_index ) )
+ return self.parse_value( columns[ index ], self.get_column_type( parser_index ) )
# if a selected index is not within columns, return None
except IndexError, index_err:
return None
- def _parse_columns_from_line( self, line ):
+ def parse_columns_from_line( self, line ):
"""
Returns a list of the desired, parsed columns.
:param line: the line to parse
@@ -188,13 +196,13 @@
selected_indeces = self.selected_column_indeces or list( xrange( len( all_columns ) ) )
parsed_columns = []
for parser_index, column_index in enumerate( selected_indeces ):
- parsed_columns.append( self._parse_column_at_index( all_columns, parser_index, column_index ) )
+ parsed_columns.append( self.parse_column_at_index( all_columns, parser_index, column_index ) )
return parsed_columns
def __iter__( self ):
parent_gen = super( ColumnarDataProvider, self ).__iter__()
for line in parent_gen:
- columns = self._parse_columns_from_line( line )
+ columns = self.parse_columns_from_line( line )
yield columns
#TODO: implement column filters here and not below - flatten hierarchy
@@ -223,6 +231,10 @@
.. note: that the subclass constructors are passed kwargs - so they're
params (limit, offset, etc.) are also applicable here.
"""
+ settings = {
+ 'column_names' : 'list:str',
+ }
+
def __init__( self, source, column_names=None, **kwargs ):
"""
:param column_names: an ordered list of strings that will be used as the keys
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/dataproviders/dataset.py
--- a/lib/galaxy/datatypes/dataproviders/dataset.py
+++ b/lib/galaxy/datatypes/dataproviders/dataset.py
@@ -141,7 +141,7 @@
"""
# metadata columns are 1-based indeces
column = getattr( self.dataset.metadata, name )
- return ( column - 1 ) if isinstance( column, int ) else None
+ return ( column - 1 ) if ( isinstance( column, int ) and column > 0 ) else None
def get_genomic_region_indeces( self, check=False ):
"""
@@ -271,6 +271,12 @@
"""
# dictionary keys when named_columns=True
COLUMN_NAMES = [ 'chrom', 'start', 'end' ]
+ settings = {
+ 'chrom_column' : 'int',
+ 'start_column' : 'int',
+ 'end_column' : 'int',
+ 'named_columns' : 'bool',
+ }
def __init__( self, dataset, chrom_column=None, start_column=None, end_column=None, named_columns=False, **kwargs ):
"""
@@ -333,6 +339,14 @@
'chrom', 'start', 'end' (and 'strand' and 'name' if available).
"""
COLUMN_NAMES = [ 'chrom', 'start', 'end', 'strand', 'name' ]
+ settings = {
+ 'chrom_column' : 'int',
+ 'start_column' : 'int',
+ 'end_column' : 'int',
+ 'strand_column' : 'int',
+ 'name_column' : 'int',
+ 'named_columns' : 'bool',
+ }
def __init__( self, dataset, chrom_column=None, start_column=None, end_column=None,
strand_column=None, name_column=None, named_columns=False, **kwargs ):
@@ -349,25 +363,40 @@
dataset_source = DatasetDataProvider( dataset )
# get genomic indeces and add strand and name
+ self.column_names = []
+ indeces = []
+ #TODO: this is sort of involved and oogly
if chrom_column == None:
chrom_column = dataset_source.get_metadata_column_index_by_name( 'chromCol' )
+ if chrom_column != None:
+ self.column_names.append( 'chrom' )
+ indeces.append( chrom_column )
if start_column == None:
start_column = dataset_source.get_metadata_column_index_by_name( 'startCol' )
+ if start_column != None:
+ self.column_names.append( 'start' )
+ indeces.append( start_column )
if end_column == None:
end_column = dataset_source.get_metadata_column_index_by_name( 'endCol' )
+ if end_column != None:
+ self.column_names.append( 'end' )
+ indeces.append( end_column )
if strand_column == None:
strand_column = dataset_source.get_metadata_column_index_by_name( 'strandCol' )
+ if strand_column != None:
+ self.column_names.append( 'strand' )
+ indeces.append( strand_column )
if name_column == None:
name_column = dataset_source.get_metadata_column_index_by_name( 'nameCol' )
- indeces = [ chrom_column, start_column, end_column, strand_column, name_column ]
+ if name_column != None:
+ self.column_names.append( 'name' )
+ indeces.append( name_column )
+
kwargs.update({ 'indeces' : indeces })
-
if not kwargs.get( 'column_types', None ):
kwargs.update({ 'column_types' : dataset_source.get_metadata_column_types( indeces=indeces ) })
self.named_columns = named_columns
- if self.named_columns:
- self.column_names = self.COLUMN_NAMES
super( IntervalDataProvider, self ).__init__( dataset_source, **kwargs )
@@ -390,6 +419,10 @@
sequence: <joined lines of nucleotide/amino data>
}
"""
+ settings = {
+ 'ids' : 'list:str',
+ }
+
def __init__( self, source, ids=None, **kwargs ):
"""
:param ids: optionally return only ids (and sequences) that are in this list.
@@ -419,6 +452,10 @@
sequence: <joined lines of nucleotide/amino data>
}
"""
+ settings = {
+ 'ids' : 'list:str',
+ }
+
def __init__( self, source, ids=None, **kwargs ):
"""
:param ids: optionally return only ids (and sequences) that are in this list.
@@ -445,6 +482,10 @@
Class that returns chrom, pos, data from a wiggle source.
"""
COLUMN_NAMES = [ 'chrom', 'pos', 'value' ]
+ settings = {
+ 'named_columns' : 'bool',
+ 'column_names' : 'list:str',
+ }
def __init__( self, source, named_columns=False, column_names=None, **kwargs ):
"""
@@ -483,6 +524,10 @@
Class that returns chrom, pos, data from a wiggle source.
"""
COLUMN_NAMES = [ 'chrom', 'pos', 'value' ]
+ settings = {
+ 'named_columns' : 'bool',
+ 'column_names' : 'list:str',
+ }
def __init__( self, source, chrom, start, end, named_columns=False, column_names=None, **kwargs ):
"""
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/dataproviders/decorators.py
--- a/lib/galaxy/datatypes/dataproviders/decorators.py
+++ b/lib/galaxy/datatypes/dataproviders/decorators.py
@@ -87,17 +87,40 @@
# log.debug( '\t\t ', fn.__doc__ )
return cls
-def dataprovider_factory( name ):
+def dataprovider_factory( name, settings=None ):
"""
- Wraps a class method and marks it as a dataprovider factory.
+ Wraps a class method and marks it as a dataprovider factory and creates a
+ function to parse query strings to __init__ arguments as the
+ `parse_query_string_settings` attribute of the factory function.
+
+ An example use of the `parse_query_string_settings`:
+ ..example::
+ kwargs = dataset.datatype.dataproviders[ provider ].parse_query_string_settings( query_kwargs )
+ return list( dataset.datatype.dataprovider( dataset, provider, **kwargs ) )
:param name: what name/key to register the factory under in `cls.dataproviders`
- :param type: any hashable var
+ :type name: any hashable var
+ :param settings: dictionary containing key/type pairs for parsing query strings
+ to __init__ arguments
+ :type settings: dictionary
"""
+ #TODO:?? use *args for settings allowing mulitple dictionaries
+ # make a function available through the name->provider dispatch to parse query strings
+ # callable like:
+ # settings_dict = dataproviders[ provider_name ].parse_query_string_settings( query_kwargs )
+ #TODO: ugh - overly complicated but the best I could think of
+ def parse_query_string_settings( query_kwargs ):
+ return _parse_query_string_settings( query_kwargs, settings )
+
#log.debug( 'dataprovider:', name )
def named_dataprovider_factory( func ):
#log.debug( 'named_dataprovider_factory:', name, '->', func.__name__ )
setattr( func, _DATAPROVIDER_METHOD_NAME_KEY, name )
+
+ setattr( func, 'parse_query_string_settings', parse_query_string_settings )
+ setattr( func, 'settings', settings )
+ #TODO: I want a way to inherit settings from the previous provider( this_name ) instead of defining over and over
+
#log.debug( '\t setting:', getattr( func, _DATAPROVIDER_METHOD_NAME_KEY ) )
@wraps( func )
def wrapped_dataprovider_factory( self, *args, **kwargs ):
@@ -105,3 +128,38 @@
return func( self, *args, **kwargs )
return wrapped_dataprovider_factory
return named_dataprovider_factory
+
+def _parse_query_string_settings( query_kwargs, settings=None ):
+ """
+ Parse the values in `query_kwargs` from strings to the proper types
+ listed in the same key in `settings`.
+ """
+ def list_from_query_string( s ):
+ # assume csv
+ return s.split( ',' )
+
+ parsers = {
+ 'int' : int,
+ 'float' : float,
+ 'bool' : bool,
+ 'list:str' : lambda s: list_from_query_string( s ),
+ 'list:int' : lambda s: [ int( i ) for i in list_from_query_string( s ) ],
+ }
+ settings = settings or {}
+ # yay! yet another set of query string parsers! <-- sarcasm
+ # work through the keys in settings finding matching keys in query_kwargs
+ # if found in both, get the expected/needed type from settings and store the new parsed value
+ # if we can't parse it (no parser, bad value), delete the key from query_kwargs so the provider will use the defaults
+ for key in settings:
+ if key in query_kwargs:
+ #TODO: this would be the place to sanitize any strings
+ query_value = query_kwargs[ key ]
+ needed_type = settings[ key ]
+ try:
+ query_kwargs[ key ] = parsers[ needed_type ]( query_value )
+ except ( KeyError, ValueError ):
+ del query_kwargs[ key ]
+
+ #TODO:?? do we want to remove query_kwarg entries NOT in settings?
+ return query_kwargs
+
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/dataproviders/line.py
--- a/lib/galaxy/datatypes/dataproviders/line.py
+++ b/lib/galaxy/datatypes/dataproviders/line.py
@@ -27,6 +27,12 @@
to return.
"""
DEFAULT_COMMENT_CHAR = '#'
+ settings = {
+ 'string_lines' : 'bool',
+ 'provide_blank' : 'bool',
+ 'comment_char' : 'str',
+ }
+
def __init__( self, source, strip_lines=True, provide_blank=False, comment_char=DEFAULT_COMMENT_CHAR, **kwargs ):
"""
:param strip_lines: remove whitespace from the beginning an ending
@@ -78,6 +84,11 @@
.. note:: the regex matches are effectively OR'd (if **any** regex matches
the line it is considered valid and will be provided).
"""
+ settings = {
+ 'regex_list' : 'list:str',
+ 'invert' : 'bool',
+ }
+
def __init__( self, source, regex_list=None, invert=False, **kwargs ):
"""
:param regex_list: list of strings or regular expression strings that will
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/interval.py
--- a/lib/galaxy/datatypes/interval.py
+++ b/lib/galaxy/datatypes/interval.py
@@ -334,20 +334,24 @@
return None
# ------------- Dataproviders
- @dataproviders.decorators.dataprovider_factory( 'genomic-region' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_dataprovider( self, dataset, **settings ):
return dataproviders.dataset.GenomicRegionDataProvider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region-map' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region-map',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_map_dataprovider( self, dataset, **settings ):
settings[ 'named_columns' ] = True
return self.genomic_region_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'interval' )
+ @dataproviders.decorators.dataprovider_factory( 'interval',
+ dataproviders.dataset.IntervalDataProvider.settings )
def interval_dataprovider( self, dataset, **settings ):
return dataproviders.dataset.IntervalDataProvider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'interval-map' )
+ @dataproviders.decorators.dataprovider_factory( 'interval-map',
+ dataproviders.dataset.IntervalDataProvider.settings )
def interval_map_dataprovider( self, dataset, **settings ):
settings[ 'named_columns' ] = True
return self.interval_dataprovider( dataset, **settings )
@@ -809,20 +813,24 @@
# ------------- Dataproviders
# redefine bc super is Tabular
- @dataproviders.decorators.dataprovider_factory( 'genomic-region' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_dataprovider( self, dataset, **settings ):
return dataproviders.dataset.GenomicRegionDataProvider( dataset, 0, 3, 4, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region-map' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region-map',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_map_dataprovider( self, dataset, **settings ):
settings[ 'named_columns' ] = True
return self.genomic_region_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'interval' )
+ @dataproviders.decorators.dataprovider_factory( 'interval',
+ dataproviders.dataset.IntervalDataProvider.settings )
def interval_dataprovider( self, dataset, **settings ):
return dataproviders.dataset.IntervalDataProvider( dataset, 0, 3, 4, 6, 2, **settings )
- @dataproviders.decorators.dataprovider_factory( 'interval-map' )
+ @dataproviders.decorators.dataprovider_factory( 'interval-map',
+ dataproviders.dataset.IntervalDataProvider.settings )
def interval_map_dataprovider( self, dataset, **settings ):
settings[ 'named_columns' ] = True
return self.interval_dataprovider( dataset, **settings )
@@ -1193,12 +1201,12 @@
return resolution
# ------------- Dataproviders
- @dataproviders.decorators.dataprovider_factory( 'wiggle' )
+ @dataproviders.decorators.dataprovider_factory( 'wiggle', dataproviders.dataset.WiggleDataProvider.settings )
def wiggle_dataprovider( self, dataset, **settings ):
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
return dataproviders.dataset.WiggleDataProvider( dataset_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'wiggle-map' )
+ @dataproviders.decorators.dataprovider_factory( 'wiggle-map', dataproviders.dataset.WiggleDataProvider.settings )
def wiggle_map_dataprovider( self, dataset, **settings ):
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
settings[ 'named_columns' ] = True
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/sequence.py
--- a/lib/galaxy/datatypes/sequence.py
+++ b/lib/galaxy/datatypes/sequence.py
@@ -15,8 +15,6 @@
from galaxy import util
from sniff import *
-from galaxy.datatypes import dataproviders
-
import pkg_resources
pkg_resources.require("simplejson")
import simplejson
@@ -399,15 +397,6 @@
f.close()
_count_split = classmethod(_count_split)
- def provider( self, dataset, data_format, **settings ):
- from galaxy.dataproviders import dataset as dataset_providers
-
- if data_format == 'id_seq':
- source = dataset_providers.DatasetDataProvider( dataset )
- return dataset_providers.FastaDataProvider( source, **settings )
-
- return super( Fasta, self ).provider( dataset, data_format, **settings )
-
class csFasta( Sequence ):
""" Class representing the SOLID Color-Space sequence ( csfasta ) """
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/sniff.py
--- a/lib/galaxy/datatypes/sniff.py
+++ b/lib/galaxy/datatypes/sniff.py
@@ -6,6 +6,7 @@
from galaxy import util
from galaxy.datatypes.checkers import *
from encodings import search_function as encodings_search_function
+from binary import Binary
log = logging.getLogger(__name__)
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/datatypes/tabular.py
--- a/lib/galaxy/datatypes/tabular.py
+++ b/lib/galaxy/datatypes/tabular.py
@@ -345,26 +345,25 @@
return vizs
# ------------- Dataproviders
- @dataproviders.decorators.dataprovider_factory( 'column' )
+ @dataproviders.decorators.dataprovider_factory( 'column', dataproviders.column.ColumnarDataProvider.settings )
def column_dataprovider( self, dataset, **settings ):
"""Uses column settings that are passed in"""
- print 'Tabular.comment_char:', settings.get( 'comment_char', None )
-
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
return dataproviders.column.ColumnarDataProvider( dataset_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'dataset-column' )
+ @dataproviders.decorators.dataprovider_factory( 'dataset-column',
+ dataproviders.column.ColumnarDataProvider.settings )
def dataset_column_dataprovider( self, dataset, **settings ):
"""Attempts to get column settings from dataset.metadata"""
return dataproviders.dataset.DatasetColumnarDataProvider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'map' )
+ @dataproviders.decorators.dataprovider_factory( 'map', dataproviders.column.MapDataProvider.settings )
def map_dataprovider( self, dataset, **settings ):
"""Uses column settings that are passed in"""
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
return dataproviders.column.MapDataProvider( dataset_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'dataset-map' )
+ @dataproviders.decorators.dataprovider_factory( 'dataset-map', dataproviders.column.MapDataProvider.settings )
def dataset_map_dataprovider( self, dataset, **settings ):
"""Attempts to get column settings from dataset.metadata"""
return dataproviders.dataset.DatasetMapDataProvider( dataset, **settings )
@@ -502,55 +501,58 @@
# ------------- Dataproviders
# sam does not use '#' to indicate comments/headers - we need to strip out those headers from the std. providers
#TODO:?? seems like there should be an easier way to do this - metadata.comment_char?
- @dataproviders.decorators.dataprovider_factory( 'line' )
+ @dataproviders.decorators.dataprovider_factory( 'line', dataproviders.line.FilteredLineDataProvider.settings )
def line_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return super( Sam, self ).line_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'regex-line' )
+ @dataproviders.decorators.dataprovider_factory( 'regex-line', dataproviders.line.RegexLineDataProvider.settings )
def regex_line_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return super( Sam, self ).regex_line_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'column' )
+ @dataproviders.decorators.dataprovider_factory( 'column', dataproviders.column.ColumnarDataProvider.settings )
def column_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return super( Sam, self ).column_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'dataset-column' )
+ @dataproviders.decorators.dataprovider_factory( 'dataset-column',
+ dataproviders.column.ColumnarDataProvider.settings )
def dataset_column_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return super( Sam, self ).dataset_column_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'map' )
+ @dataproviders.decorators.dataprovider_factory( 'map', dataproviders.column.MapDataProvider.settings )
def map_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return super( Sam, self ).map_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'dataset-map' )
+ @dataproviders.decorators.dataprovider_factory( 'dataset-map', dataproviders.column.MapDataProvider.settings )
def dataset_map_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return super( Sam, self ).dataset_map_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'header' )
+ @dataproviders.decorators.dataprovider_factory( 'header', dataproviders.line.RegexLineDataProvider.settings )
def header_dataprovider( self, dataset, **settings ):
dataset_source = dataproviders.dataset.DatasetDataProvider( dataset )
headers_source = dataproviders.line.RegexLineDataProvider( dataset_source, regex_list=[ '^@' ] )
return dataproviders.line.RegexLineDataProvider( headers_source, **settings )
- @dataproviders.decorators.dataprovider_factory( 'id-seq-qual' )
+ @dataproviders.decorators.dataprovider_factory( 'id-seq-qual', map_dataprovider.settings )
def id_seq_qual_dataprovider( self, dataset, **settings ):
# provided as an example of a specified column map (w/o metadata)
settings[ 'indeces' ] = [ 0, 9, 10 ]
settings[ 'column_names' ] = [ 'id', 'seq', 'qual' ]
return self.map_dataprovider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return dataproviders.dataset.GenomicRegionDataProvider( dataset, 2, 3, 3, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region-map' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region-map',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_map_dataprovider( self, dataset, **settings ):
settings[ 'comment_char' ] = '@'
return dataproviders.dataset.GenomicRegionDataProvider( dataset, 2, 3, 3, True, **settings )
@@ -621,11 +623,13 @@
return False
# ------------- Dataproviders
- @dataproviders.decorators.dataprovider_factory( 'genomic-region' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_dataprovider( self, dataset, **settings ):
return dataproviders.dataset.GenomicRegionDataProvider( dataset, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region-map' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region-map',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_map_dataprovider( self, dataset, **settings ):
settings[ 'named_columns' ] = True
return self.genomic_region_dataprovider( dataset, **settings )
@@ -668,11 +672,13 @@
dataset.metadata.sample_names = line.split()[ 9: ]
# ------------- Dataproviders
- @dataproviders.decorators.dataprovider_factory( 'genomic-region' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_dataprovider( self, dataset, **settings ):
return dataproviders.dataset.GenomicRegionDataProvider( dataset, 0, 1, 1, **settings )
- @dataproviders.decorators.dataprovider_factory( 'genomic-region-map' )
+ @dataproviders.decorators.dataprovider_factory( 'genomic-region-map',
+ dataproviders.dataset.GenomicRegionDataProvider.settings )
def genomic_region_map_dataprovider( self, dataset, **settings ):
settings[ 'named_columns' ] = True
return self.genomic_region_dataprovider( dataset, **settings )
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/jobs/__init__.py
--- a/lib/galaxy/jobs/__init__.py
+++ b/lib/galaxy/jobs/__init__.py
@@ -692,7 +692,10 @@
incoming['__user_email__'] = incoming['userEmail'] = user_email
incoming['__user_name__'] = user_name
# Build params, done before hook so hook can use
- param_dict = self.tool.build_param_dict( incoming, inp_data, out_data, self.get_output_fnames(), self.working_directory )
+ param_dict = self.tool.build_param_dict( incoming,
+ inp_data, out_data,
+ self.get_output_fnames(),
+ self.working_directory )
# Certain tools require tasks to be completed prior to job execution
# ( this used to be performed in the "exec_before_job" hook, but hooks are deprecated ).
self.tool.exec_before_job( self.queue.app, inp_data, out_data, param_dict )
@@ -919,8 +922,6 @@
return self.fail( "Job %s's output dataset(s) could not be read" % job.id )
job_context = ExpressionContext( dict( stdout = job.stdout, stderr = job.stderr ) )
- #DBTODO unused
- #job_tool = self.app.toolbox.tools_by_id.get( job.tool_id, None )
for dataset_assoc in job.output_datasets + job.output_library_datasets:
context = self.get_dataset_finish_context( job_context, dataset_assoc.dataset.dataset )
#should this also be checking library associations? - can a library item be added from a history before the job has ended? - lets not allow this to occur
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/jobs/handler.py
--- a/lib/galaxy/jobs/handler.py
+++ b/lib/galaxy/jobs/handler.py
@@ -10,7 +10,7 @@
from sqlalchemy.sql.expression import and_, or_, select, func
-from galaxy import util, model
+from galaxy import model
from galaxy.jobs import Sleeper, JobWrapper, TaskWrapper, JobDestination
log = logging.getLogger( __name__ )
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/model/__init__.py
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -3569,7 +3569,7 @@
def repository_dependencies_being_installed( self ):
required_repositories_being_installed = []
for required_repository in self.repository_dependencies:
- if tool_dependency.status == ToolDependency.installation_status.INSTALLING:
+ if required_repository.status == self.installation_status.INSTALLING:
required_repositories_being_installed.append( required_repository )
return required_repositories_being_installed
@property
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/model/mapping.py
--- a/lib/galaxy/model/mapping.py
+++ b/lib/galaxy/model/mapping.py
@@ -16,6 +16,7 @@
from sqlalchemy.orm.collections import attribute_mapped_collection
from galaxy import model
+from galaxy.model.orm import dialect_to_egg
from galaxy.model.custom_types import JSONType, MetadataType, TrimmedString, UUIDType
from galaxy.security import GalaxyRBACAgent
from galaxy.util.bunch import Bunch
@@ -29,11 +30,6 @@
# For backward compatibility with "context.current"
context.current = Session
-dialect_to_egg = {
- "sqlite" : "pysqlite>=2",
- "postgres" : "psycopg2",
- "mysql" : "MySQL_python"
-}
# NOTE REGARDING TIMESTAMPS:
# It is currently difficult to have the timestamps calculated by the
@@ -1616,17 +1612,27 @@
primaryjoin=( model.LibraryDatasetDatasetInfoAssociation.table.c.form_values_id == model.FormValues.table.c.id ) )
) )
-mapper( model.JobToInputDatasetAssociation, model.JobToInputDatasetAssociation.table,
- properties=dict( job=relation( model.Job ), dataset=relation( model.HistoryDatasetAssociation, lazy=False, backref="dependent_jobs" ) ) )
+mapper( model.JobToInputDatasetAssociation,
+ model.JobToInputDatasetAssociation.table, properties=dict(
+ job=relation( model.Job ), dataset=relation(
+ model.HistoryDatasetAssociation, lazy=False,
+ backref="dependent_jobs" ) ) )
-mapper( model.JobToOutputDatasetAssociation, model.JobToOutputDatasetAssociation.table,
- properties=dict( job=relation( model.Job ), dataset=relation( model.HistoryDatasetAssociation, lazy=False ) ) )
+mapper( model.JobToOutputDatasetAssociation,
+ model.JobToOutputDatasetAssociation.table, properties=dict(
+ job=relation( model.Job ), dataset=relation(
+ model.HistoryDatasetAssociation, lazy=False ) ) )
-mapper( model.JobToInputLibraryDatasetAssociation, model.JobToInputLibraryDatasetAssociation.table,
- properties=dict( job=relation( model.Job ), dataset=relation( model.LibraryDatasetDatasetAssociation, lazy=False, backref="dependent_jobs" ) ) )
+mapper( model.JobToInputLibraryDatasetAssociation,
+ model.JobToInputLibraryDatasetAssociation.table, properties=dict(
+ job=relation( model.Job ), dataset=relation(
+ model.LibraryDatasetDatasetAssociation, lazy=False,
+ backref="dependent_jobs" ) ) )
-mapper( model.JobToOutputLibraryDatasetAssociation, model.JobToOutputLibraryDatasetAssociation.table,
- properties=dict( job=relation( model.Job ), dataset=relation( model.LibraryDatasetDatasetAssociation, lazy=False ) ) )
+mapper( model.JobToOutputLibraryDatasetAssociation,
+ model.JobToOutputLibraryDatasetAssociation.table, properties=dict(
+ job=relation( model.Job ), dataset=relation(
+ model.LibraryDatasetDatasetAssociation, lazy=False ) ) )
mapper( model.JobParameter, model.JobParameter.table )
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/model/migrate/check.py
--- a/lib/galaxy/model/migrate/check.py
+++ b/lib/galaxy/model/migrate/check.py
@@ -12,16 +12,13 @@
from sqlalchemy.exc import NoSuchTableError
from migrate.versioning import repository, schema
+from galaxy.model.orm import dialect_to_egg
+
log = logging.getLogger( __name__ )
# path relative to galaxy
migrate_repository_directory = os.path.dirname( __file__ ).replace( os.getcwd() + os.path.sep, '', 1 )
migrate_repository = repository.Repository( migrate_repository_directory )
-dialect_to_egg = {
- "sqlite" : "pysqlite>=2",
- "postgres" : "psycopg2",
- "mysql" : "MySQL_python"
-}
def create_or_verify_database( url, galaxy_config_file, engine_options={}, app=None ):
"""
@@ -47,6 +44,7 @@
# Let this go, it could possibly work with db's we don't support
log.error( "database_connection contains an unknown SQLAlchemy database dialect: %s" % dialect )
# Create engine and metadata
+ print url, engine_options
engine = create_engine( url, **engine_options )
meta = MetaData( bind=engine )
# Try to load dataset table
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/model/orm/__init__.py
--- a/lib/galaxy/model/orm/__init__.py
+++ b/lib/galaxy/model/orm/__init__.py
@@ -7,3 +7,10 @@
import sqlalchemy.exc
from sqlalchemy.ext.orderinglist import ordering_list
+
+dialect_to_egg = {
+ "sqlite" : "pysqlite>=2",
+ "postgres" : "psycopg2",
+ "postgresql" : "psycopg2",
+ "mysql" : "MySQL_python"
+}
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/tools/__init__.py
--- a/lib/galaxy/tools/__init__.py
+++ b/lib/galaxy/tools/__init__.py
@@ -816,6 +816,7 @@
"""
def __init__( self ):
self.page = 0
+ self.rerun_remap_job_id = None
self.inputs = None
def encode( self, tool, app, secure=True ):
"""
@@ -825,6 +826,7 @@
# page in that dict
value = params_to_strings( tool.inputs, self.inputs, app )
value["__page__"] = self.page
+ value["__rerun_remap_job_id__"] = self.rerun_remap_job_id
value = simplejson.dumps( value )
# Make it secure
if secure:
@@ -846,6 +848,10 @@
# Restore from string
values = json_fix( simplejson.loads( value ) )
self.page = values.pop( "__page__" )
+ if '__rerun_remap_job_id__' in values:
+ self.rerun_remap_job_id = values.pop( "__rerun_remap_job_id__" )
+ else:
+ self.rerun_remap_job_id = None
self.inputs = params_from_strings( tool.inputs, values, app, ignore_errors=True )
class ToolOutput( object ):
@@ -933,6 +939,7 @@
self.input_required = False
self.display_interface = True
self.require_login = False
+ self.rerun = False
# Define a place to keep track of all input These
# differ from the inputs dictionary in that inputs can be page
# elements like conditionals, but input_params are basic form
@@ -1521,7 +1528,8 @@
elif ( re.search( "fatal", err_level, re.IGNORECASE ) ):
return_level = StdioErrorLevel.FATAL
else:
- log.debug( "Error level %s did not match warning/fatal" % err_level )
+ log.debug( "Tool %s: error level %s did not match log/warning/fatal" %
+ ( self.id, err_level ) )
except Exception:
log.error( "Exception in parse_error_level "
+ str(sys.exc_info() ) )
@@ -1933,7 +1941,10 @@
# If we've completed the last page we can execute the tool
elif state.page == self.last_page:
try:
- _, out_data = self.execute( trans, incoming=params, history=history )
+ rerun_remap_job_id = None
+ if 'rerun_remap_job_id' in incoming:
+ rerun_remap_job_id = trans.app.security.decode_id(incoming['rerun_remap_job_id'])
+ _, out_data = self.execute( trans, incoming=params, history=history, rerun_remap_job_id=rerun_remap_job_id )
except httpexceptions.HTTPFound, e:
#if it's a paste redirect exception, pass it up the stack
raise e
@@ -2502,7 +2513,6 @@
datatypes_registry = self.app.datatypes_registry,
tool = self,
name = name )
-
if data:
for child in data.children:
param_dict[ "_CHILD___%s___%s" % ( name, child.designation ) ] = DatasetFilenameWrapper( child )
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/tools/actions/__init__.py
--- a/lib/galaxy/tools/actions/__init__.py
+++ b/lib/galaxy/tools/actions/__init__.py
@@ -1,15 +1,16 @@
+import os
+import galaxy.tools
+
+from galaxy.exceptions import ObjectInvalid
from galaxy.model import LibraryDatasetDatasetAssociation
-from galaxy.util.bunch import Bunch
+from galaxy.tools.parameters import DataToolParameter, SelectToolParameter
+from galaxy.tools.parameters.grouping import Conditional, Repeat
+from galaxy.util.json import from_json_string
+from galaxy.util.json import to_json_string
+from galaxy.util.none_like import NoneDataset
from galaxy.util.odict import odict
-from galaxy.util.json import to_json_string
-from galaxy.tools.parameters import *
-from galaxy.tools.parameters.grouping import *
from galaxy.util.template import fill_template
-from galaxy.util.none_like import NoneDataset
from galaxy.web import url_for
-from galaxy.exceptions import ObjectInvalid
-import galaxy.tools
-from types import *
import logging
log = logging.getLogger( __name__ )
@@ -107,7 +108,7 @@
tool.visit_inputs( param_values, visitor )
return input_datasets
- def execute(self, tool, trans, incoming={}, return_job=False, set_output_hid=True, set_output_history=True, history=None, job_params=None ):
+ def execute(self, tool, trans, incoming={}, return_job=False, set_output_hid=True, set_output_history=True, history=None, job_params=None, rerun_remap_job_id=None):
"""
Executes a tool, creating job and tool outputs, associating them, and
submitting the job to the job queue. If history is not specified, use
@@ -409,6 +410,40 @@
job.params = to_json_string( job_params )
job.set_handler(tool.get_job_handler(job_params))
trans.sa_session.add( job )
+ # Now that we have a job id, we can remap any outputs if this is a rerun and the user chose to continue dependent jobs
+ # This functionality requires tracking jobs in the database.
+ if trans.app.config.track_jobs_in_database and rerun_remap_job_id is not None:
+ try:
+ old_job = trans.sa_session.query( trans.app.model.Job ).get(rerun_remap_job_id)
+ assert old_job is not None, '(%s/%s): Old job id is invalid' % (rerun_remap_job_id, job.id)
+ assert old_job.tool_id == job.tool_id, '(%s/%s): Old tool id (%s) does not match rerun tool id (%s)' % (old_job.id, job.id, old_job.tool_id, job.tool_id)
+ if trans.user is not None:
+ assert old_job.user_id == trans.user.id, '(%s/%s): Old user id (%s) does not match rerun user id (%s)' % (old_job.id, job.id, old_job.user_id, trans.user.id)
+ elif trans.user is None and type( galaxy_session ) == trans.model.GalaxySession:
+ assert old_job.session_id == galaxy_session.id, '(%s/%s): Old session id (%s) does not match rerun session id (%s)' % (old_job.id, job.id, old_job.session_id, galaxy_session.id)
+ else:
+ raise Exception('(%s/%s): Remapping via the API is not (yet) supported' % (old_job.id, job.id))
+ for jtod in old_job.output_datasets:
+ for (job_to_remap, jtid) in [(jtid.job, jtid) for jtid in jtod.dataset.dependent_jobs]:
+ if (trans.user is not None and job_to_remap.user_id == trans.user.id) or (trans.user is None and job_to_remap.session_id == galaxy_session.id):
+ if job_to_remap.state == job_to_remap.states.PAUSED:
+ job_to_remap.state = job_to_remap.states.NEW
+ for hda in [ dep_jtod.dataset for dep_jtod in job_to_remap.output_datasets ]:
+ if hda.state == hda.states.PAUSED:
+ hda.state = hda.states.NEW
+ hda.info = None
+ for p in job_to_remap.parameters:
+ if p.name == jtid.name and p.value == str(jtod.dataset.id):
+ p.value = str(out_data[jtod.name].id)
+ jtid.dataset = out_data[jtod.name]
+ jtid.dataset.hid = jtod.dataset.hid
+ log.info('Job %s input HDA %s remapped to new HDA %s' % (job_to_remap.id, jtod.dataset.id, jtid.dataset.id))
+ trans.sa_session.add(job_to_remap)
+ trans.sa_session.add(jtid)
+ jtod.dataset.visible = False
+ trans.sa_session.add(jtod)
+ except Exception, e:
+ log.exception('Cannot remap rerun dependencies.')
trans.sa_session.flush()
# Some tools are not really executable, but jobs are still created for them ( for record keeping ).
# Examples include tools that redirect to other applications ( epigraph ). These special tools must
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/tools/actions/history_imp_exp.py
--- a/lib/galaxy/tools/actions/history_imp_exp.py
+++ b/lib/galaxy/tools/actions/history_imp_exp.py
@@ -9,7 +9,7 @@
class ImportHistoryToolAction( ToolAction ):
"""Tool action used for importing a history to an archive. """
- def execute( self, tool, trans, incoming = {}, set_output_hid = False, overwrite = True, history=None ):
+ def execute( self, tool, trans, incoming = {}, set_output_hid = False, overwrite = True, history=None, **kwargs ):
#
# Create job.
#
@@ -57,7 +57,7 @@
class ExportHistoryToolAction( ToolAction ):
"""Tool action used for exporting a history to an archive. """
- def execute( self, tool, trans, incoming = {}, set_output_hid = False, overwrite = True, history=None ):
+ def execute( self, tool, trans, incoming = {}, set_output_hid = False, overwrite = True, history=None, **kwargs ):
#
# Get history to export.
#
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/tools/actions/metadata.py
--- a/lib/galaxy/tools/actions/metadata.py
+++ b/lib/galaxy/tools/actions/metadata.py
@@ -9,7 +9,7 @@
class SetMetadataToolAction( ToolAction ):
"""Tool action used for setting external metadata on an existing dataset"""
- def execute( self, tool, trans, incoming={}, set_output_hid=False, overwrite=True, history=None, job_params=None ):
+ def execute( self, tool, trans, incoming={}, set_output_hid=False, overwrite=True, history=None, job_params=None, **kwargs ):
"""
Execute using a web transaction.
"""
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/tools/actions/upload.py
--- a/lib/galaxy/tools/actions/upload.py
+++ b/lib/galaxy/tools/actions/upload.py
@@ -5,7 +5,7 @@
log = logging.getLogger( __name__ )
class UploadToolAction( ToolAction ):
- def execute( self, tool, trans, incoming={}, set_output_hid = True, history=None ):
+ def execute( self, tool, trans, incoming={}, set_output_hid = True, history=None, **kwargs ):
dataset_upload_inputs = []
for input_name, input in tool.inputs.iteritems():
if input.type == "upload_dataset":
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/visualization/data_providers/registry.py
--- a/lib/galaxy/visualization/data_providers/registry.py
+++ b/lib/galaxy/visualization/data_providers/registry.py
@@ -32,7 +32,7 @@
"bigwig": genome.BigWigDataProvider,
"bigbed": genome.BigBedDataProvider,
- "column": ColumnDataProvider
+ "column_with_stats": ColumnDataProvider
}
def get_data_provider( self, trans, name=None, source='data', raw=False, original_dataset=None ):
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/visualization/registry.py
--- a/lib/galaxy/visualization/registry.py
+++ b/lib/galaxy/visualization/registry.py
@@ -15,22 +15,27 @@
log = logging.getLogger( __name__ )
__TODO__ = """
- BUGS:
- anon users clicking a viz link gets 'must be' msg in galaxy_main (w/ masthead)
- should not show visualizations (no icon)?
- newick files aren't being sniffed prop? - datatype is txt
+BUGS:
+ anon users clicking a viz link gets 'must be' msg in galaxy_main (w/ masthead)
+ should not show visualizations (no icon)?
+ newick files aren't being sniffed prop? - datatype is txt
- have parsers create objects instead of dicts
- allow data_sources with no model_class but have tests (isAdmin, etc.)
- maybe that's an instance of User model_class?
- some confused vocabulary in docs, var names
- tests:
- anding, grouping, not
- data_sources:
- lists of
- add description element to visualization.
+have parsers create objects instead of dicts
+allow data_sources with no model_class but have tests (isAdmin, etc.)
+ maybe that's an instance of User model_class?
+some confused vocabulary in docs, var names
+tests:
+ anding, grouping, not
+data_sources:
+ lists of
+add description element to visualization.
+
+TESTS to add:
+ has dataprovider
+ user is admin
"""
+# ------------------------------------------------------------------- the registry
class VisualizationsRegistry( object ):
"""
Main responsibilities are:
@@ -93,6 +98,45 @@
"""
self.listings = VisualizationsConfigParser.parse( self.configuration_filepath )
+ def get_visualization( self, trans, visualization_name, target_object ):
+ """
+ Return data to build a url to the visualization with the given
+ `visualization_name` if it's applicable to `target_object` or
+ `None` if it's not.
+ """
+ # a little weird to pass trans because this registry is part of the trans.app
+ listing_data = self.listings.get( visualization_name, None )
+ if not listing_data:
+ return None
+
+ data_sources = listing_data[ 'data_sources' ]
+ for data_source in data_sources:
+ # currently a model class is required
+ model_class = data_source[ 'model_class' ]
+ if not isinstance( target_object, model_class ):
+ continue
+
+ # tests are optional - default is the above class test
+ tests = data_source[ 'tests' ]
+ if tests and not self.is_object_applicable( trans, target_object, tests ):
+ continue
+
+ param_data = data_source[ 'to_params' ]
+ url = self.get_visualization_url( trans, target_object, visualization_name, param_data )
+ link_text = listing_data.get( 'link_text', None )
+ if not link_text:
+ # default to visualization name, titlecase, and replace underscores
+ link_text = visualization_name.title().replace( '_', ' ' )
+ render_location = listing_data.get( 'render_location' )
+ # remap some of these vars for direct use in ui.js, PopupMenu (e.g. text->html)
+ return {
+ 'href' : url,
+ 'html' : link_text,
+ 'target': render_location
+ }
+
+ return None
+
# -- building links to visualizations from objects --
def get_visualizations( self, trans, target_object ):
"""
@@ -100,36 +144,11 @@
the urls to call in order to render the visualizations.
"""
#TODO:?? a list of objects? YAGNI?
- # a little weird to pass trans because this registry is part of the trans.app
applicable_visualizations = []
- for vis_name, listing_data in self.listings.items():
-
- data_sources = listing_data[ 'data_sources' ]
- for data_source in data_sources:
- # currently a model class is required
- model_class = data_source[ 'model_class' ]
- if not isinstance( target_object, model_class ):
- continue
-
- # tests are optional - default is the above class test
- tests = data_source[ 'tests' ]
- if tests and not self.is_object_applicable( trans, target_object, tests ):
- continue
-
- param_data = data_source[ 'to_params' ]
- url = self.get_visualization_url( trans, target_object, vis_name, param_data )
- link_text = listing_data.get( 'link_text', None )
- if not link_text:
- # default to visualization name, titlecase, and replace underscores
- link_text = vis_name.title().replace( '_', ' ' )
- render_location = listing_data.get( 'render_location' )
- # remap some of these vars for direct use in ui.js, PopupMenu (e.g. text->html)
- applicable_visualizations.append({
- 'href' : url,
- 'html' : link_text,
- 'target': render_location
- })
-
+ for vis_name in self.listings:
+ url_data = self.get_visualization( trans, vis_name, target_object )
+ if url_data:
+ applicable_visualizations.append( url_data )
return applicable_visualizations
def is_object_applicable( self, trans, target_object, data_source_tests ):
@@ -151,10 +170,11 @@
# convert datatypes to their actual classes (for use with isinstance)
test_result = trans.app.datatypes_registry.get_datatype_class_by_name( test_result )
if not test_result:
- # warn if can't find class, but continue
+ # warn if can't find class, but continue (with other tests)
log.warn( 'visualizations_registry cannot find class (%s) for applicability test', test_result )
continue
+ #NOTE: tests are OR'd, if any test passes - the visualization can be applied
if test_fn( target_object, test_result ):
#log.debug( 'test passed' )
return True
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/webapps/galaxy/api/datasets.py
--- a/lib/galaxy/webapps/galaxy/api/datasets.py
+++ b/lib/galaxy/webapps/galaxy/api/datasets.py
@@ -6,6 +6,7 @@
from galaxy.web.base.controller import BaseAPIController, UsesVisualizationMixin, UsesHistoryDatasetAssociationMixin
from galaxy.web.base.controller import UsesHistoryMixin
from galaxy.web.framework.helpers import is_true
+from galaxy.datatypes import dataproviders
import logging
log = logging.getLogger( __name__ )
@@ -217,10 +218,24 @@
return msg
registry = trans.app.data_provider_registry
+
# allow the caller to specifiy which provider is used
- if provider and provider in registry.dataset_type_name_to_data_provider:
- data_provider = registry.dataset_type_name_to_data_provider[ provider ]( dataset )
- # or have it look up by datatype
+ # pulling from the original providers if possible, then the new providers
+ if provider:
+ if provider in registry.dataset_type_name_to_data_provider:
+ data_provider = registry.dataset_type_name_to_data_provider[ provider ]( dataset )
+
+ elif dataset.datatype.has_dataprovider( provider ):
+ kwargs = dataset.datatype.dataproviders[ provider ].parse_query_string_settings( kwargs )
+ # use dictionary to allow more than the data itself to be returned (data totals, other meta, etc.)
+ return {
+ 'data': list( dataset.datatype.dataprovider( dataset, provider, **kwargs ) )
+ }
+
+ else:
+ raise dataproviders.exceptions.NoProviderAvailable( dataset.datatype, provider )
+
+ # no provider name: look up by datatype
else:
data_provider = registry.get_data_provider( trans, raw=True, original_dataset=dataset )
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/webapps/galaxy/api/library_contents.py
--- a/lib/galaxy/webapps/galaxy/api/library_contents.py
+++ b/lib/galaxy/webapps/galaxy/api/library_contents.py
@@ -220,7 +220,8 @@
return { 'error' : 'user has no permission to add to library folder (%s)' %( folder_id ) }
ldda = self.copy_hda_to_library_folder( trans, hda, folder, ldda_message=ldda_message )
- rval = ldda.get_api_value()
+ ldda_dict = ldda.get_api_value()
+ rval = trans.security.encode_dict_ids( ldda_dict )
except Exception, exc:
#TODO: grrr...
@@ -234,7 +235,6 @@
return rval
-
@web.expose_api
def update( self, trans, id, library_id, payload, **kwd ):
"""
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/webapps/galaxy/api/provenance.py
--- a/lib/galaxy/webapps/galaxy/api/provenance.py
+++ b/lib/galaxy/webapps/galaxy/api/provenance.py
@@ -3,13 +3,13 @@
"""
import logging
from galaxy import web
-from galaxy.web.base.controller import BaseAPIController
+from galaxy.web.base.controller import BaseAPIController, UsesHistoryMixin
from paste.httpexceptions import HTTPNotImplemented, HTTPBadRequest
log = logging.getLogger( __name__ )
-class BaseProvenanceController( BaseAPIController ):
+class BaseProvenanceController( BaseAPIController, UsesHistoryMixin ):
"""
"""
@web.expose_api
@@ -43,7 +43,7 @@
item = item.copied_from_library_dataset_dataset_association
return {
"id" : trans.security.encode_id(item.id),
- "uuid" : item.dataset.uuid,
+ "uuid" : ( lambda uuid: str( uuid ) if uuid else None )( item.dataset.uuid),
"tool_id" : item.creating_job.tool_id,
"parameters" : self._get_job_record(trans, item.creating_job, follow)
}
@@ -59,7 +59,7 @@
else:
out[in_d.name] = {
"id" : trans.security.encode_id(in_d.dataset.id),
- "uuid" : in_d.dataset.dataset.uuid
+ "uuid" : ( lambda uuid: str( uuid ) if uuid else None )( in_d.dataset.dataset.uuid )
}
return out
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/webapps/galaxy/api/tool_shed_repositories.py
--- a/lib/galaxy/webapps/galaxy/api/tool_shed_repositories.py
+++ b/lib/galaxy/webapps/galaxy/api/tool_shed_repositories.py
@@ -9,6 +9,7 @@
from tool_shed.galaxy_install import repository_util
from tool_shed.util import common_util
+from tool_shed.util import encoding_util
import tool_shed.util.shed_util_common as suc
log = logging.getLogger( __name__ )
@@ -179,6 +180,11 @@
# Get the information about the Galaxy components (e.g., tool pane section, tool config file, etc) that will contain the repository information.
install_repository_dependencies = payload.get( 'install_repository_dependencies', False )
install_tool_dependencies = payload.get( 'install_tool_dependencies', False )
+ if install_tool_dependencies:
+ if trans.app.config.tool_dependency_dir is None:
+ no_tool_dependency_dir_message = "Tool dependencies can be automatically installed only if you set the value of your 'tool_dependency_dir' "
+ no_tool_dependency_dir_message += "setting in your Galaxy configuration file (universe_wsgi.ini) and restart your Galaxy server."
+ raise HTTPBadRequest( detail=no_tool_dependency_dir_message )
new_tool_panel_section = payload.get( 'new_tool_panel_section_label', '' )
shed_tool_conf = payload.get( 'shed_tool_conf', None )
if shed_tool_conf:
@@ -211,13 +217,8 @@
tool_path=tool_path,
tool_shed_url=tool_shed_url )
# Create the tool_shed_repository database records and gather additional information for repository installation.
- created_or_updated_tool_shed_repositories, tool_panel_section_keys, repo_info_dicts, filtered_repo_info_dicts, message = \
+ created_or_updated_tool_shed_repositories, tool_panel_section_keys, repo_info_dicts, filtered_repo_info_dicts = \
repository_util.handle_tool_shed_repositories( trans, installation_dict, using_api=True )
- if message and len( repo_info_dicts ) == 1:
- # We're attempting to install a single repository that has already been installed into this Galaxy instance.
- log.error( message, exc_info=True )
- trans.response.status = 500
- return dict( status='error', error=message )
if created_or_updated_tool_shed_repositories:
# Build the dictionary of information necessary for installing the repositories.
installation_dict = dict( created_or_updated_tool_shed_repositories=created_or_updated_tool_shed_repositories,
@@ -244,7 +245,7 @@
# order the list of tsr_ids to ensure all repositories install in the required order.
tsr_ids = [ trans.security.encode_id( tool_shed_repository.id ) for tool_shed_repository in tool_shed_repositories ]
ordered_tsr_ids, ordered_repo_info_dicts, ordered_tool_panel_section_keys = \
- repository_util.order_components_for_installation( trans, tsr_ids, repo_info_dicts, tool_panel_section_keys )
+ repository_util.order_components_for_installation( trans, tsr_ids, repo_info_dicts, tool_panel_section_keys=tool_panel_section_keys )
# Install the repositories, keeping track of each one for later display.
for index, tsr_id in enumerate( ordered_tsr_ids ):
tool_shed_repository = trans.sa_session.query( trans.model.ToolShedRepository ).get( trans.security.decode_id( tsr_id ) )
@@ -266,11 +267,7 @@
action='show',
id=trans.security.encode_id( tool_shed_repository.id ) )
installed_tool_shed_repositories.append( tool_shed_repository_dict )
- elif message:
- log.error( message, exc_info=True )
- trans.response.status = 500
- return dict( status='error', error=message )
- elif not created_or_updated_tool_shed_repositories and not message:
+ else:
# We're attempting to install more than 1 repository, and all of them have already been installed.
return dict( status='error', error='All repositories that you are attempting to install have been previously installed.' )
# Display the list of installed repositories.
@@ -362,3 +359,56 @@
elif isinstance( installed_tool_shed_repositories, list ):
all_installed_tool_shed_repositories.extend( installed_tool_shed_repositories )
return all_installed_tool_shed_repositories
+
+ @web.expose_api
+ def repair_repository_revision( self, trans, payload, **kwd ):
+ """
+ POST /api/tool_shed_repositories/repair_repository_revision
+ Repair a specified repository revision previously installed into Galaxy.
+
+ :param key: the current Galaxy admin user's API key
+
+ The following parameters are included in the payload.
+ :param tool_shed_url (required): the base URL of the Tool Shed from which the Repository was installed
+ :param name (required): the name of the Repository
+ :param owner (required): the owner of the Repository
+ :param changset_revision (required): the changset_revision of the RepositoryMetadata object associated with the Repository
+ """
+ api_key = kwd.get( 'key', None )
+ # Get the information about the repository to be installed from the payload.
+ tool_shed_url = payload.get( 'tool_shed_url', '' )
+ if not tool_shed_url:
+ raise HTTPBadRequest( detail="Missing required parameter 'tool_shed_url'." )
+ name = payload.get( 'name', '' )
+ if not name:
+ raise HTTPBadRequest( detail="Missing required parameter 'name'." )
+ owner = payload.get( 'owner', '' )
+ if not owner:
+ raise HTTPBadRequest( detail="Missing required parameter 'owner'." )
+ changeset_revision = payload.get( 'changeset_revision', '' )
+ if not changeset_revision:
+ raise HTTPBadRequest( detail="Missing required parameter 'changeset_revision'." )
+ tool_shed_repositories = []
+ tool_shed_repository = suc.get_tool_shed_repository_by_shed_name_owner_changeset_revision( trans.app, tool_shed_url, name, owner, changeset_revision )
+ repair_dict = repository_util.get_repair_dict( trans, tool_shed_repository )
+ ordered_tsr_ids = repair_dict.get( 'ordered_tsr_ids', [] )
+ ordered_repo_info_dicts = repair_dict.get( 'ordered_repo_info_dicts', [] )
+ if ordered_tsr_ids and ordered_repo_info_dicts:
+ repositories_for_repair = []
+ for index, tsr_id in enumerate( ordered_tsr_ids ):
+ repository = trans.sa_session.query( trans.model.ToolShedRepository ).get( trans.security.decode_id( tsr_id ) )
+ repo_info_dict = ordered_repo_info_dicts[ index ]
+ # TODO: handle errors in repair_dict.
+ repair_dict = repository_util.repair_tool_shed_repository( trans,
+ repository,
+ encoding_util.tool_shed_encode( repo_info_dict ) )
+ repository_dict = repository.get_api_value( value_mapper=default_tool_shed_repository_value_mapper( trans, repository ) )
+ repository_dict[ 'url' ] = web.url_for( controller='tool_shed_repositories',
+ action='show',
+ id=trans.security.encode_id( repository.id ) )
+ if repair_dict:
+ errors = repair_dict.get( repository.name, [] )
+ repository_dict[ 'errors_attempting_repair' ] = ' '.join( errors )
+ tool_shed_repositories.append( repository_dict )
+ # Display the list of repaired repositories.
+ return tool_shed_repositories
diff -r 320ae026f73a849c77a580410a5a3d6927ef1b91 -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 lib/galaxy/webapps/galaxy/buildapp.py
--- a/lib/galaxy/webapps/galaxy/buildapp.py
+++ b/lib/galaxy/webapps/galaxy/buildapp.py
@@ -163,12 +163,13 @@
webapp.mapper.connect("workflow_dict", '/api/workflows/download/{workflow_id}', controller='workflows', action='workflow_dict', conditions=dict(method=['GET']))
# Galaxy API for tool shed features.
webapp.mapper.resource( 'tool_shed_repository',
- 'tool_shed_repositories',
- controller='tool_shed_repositories',
- name_prefix='tool_shed_repository_',
- path_prefix='/api',
- new={ 'install_repository_revision' : 'POST' },
- parent_resources=dict( member_name='tool_shed_repository', collection_name='tool_shed_repositories' ) )
+ 'tool_shed_repositories',
+ member={ 'repair_repository_revision' : 'POST' },
+ controller='tool_shed_repositories',
+ name_prefix='tool_shed_repository_',
+ path_prefix='/api',
+ new={ 'install_repository_revision' : 'POST' },
+ parent_resources=dict( member_name='tool_shed_repository', collection_name='tool_shed_repositories' ) )
# Connect logger from app
if app.trace_logger:
webapp.trace_logger = app.trace_logger
This diff is so big that we needed to truncate the remainder.
https://bitbucket.org/galaxy/galaxy-central/commits/5f24b2c4f38b/
Changeset: 5f24b2c4f38b
Branch: search
User: Kyle Ellrott
Date: 2013-06-27 21:00:27
Summary: Fixing the job input/output values to format that is consistant with format used in other areas of galaxy.
Affected #: 1 file
diff -r 460c7dc52f92abac4d9ea9e5700dc8238b2a7fc4 -r 5f24b2c4f38bd65453cccad0b9bf526eff315918 lib/galaxy/model/__init__.py
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -372,10 +372,10 @@
input_dict = {}
for i in self.input_datasets:
if i.dataset is not None:
- input_dict[i.name] = {"hda_id" : i.dataset.id}
+ input_dict[i.name] = {"id" : i.dataset.id, "src" : "hda"}
for i in self.input_library_datasets:
if i.dataset is not None:
- input_dict[i.name] = {"ldda_id" : i.dataset.id}
+ input_dict[i.name] = {"id" : i.dataset.id, "src" : "ldda"}
for k in input_dict:
if k in param_dict:
del param_dict[k]
@@ -384,10 +384,10 @@
output_dict = {}
for i in self.output_datasets:
if i.dataset is not None:
- output_dict[i.name] = {"hda_id" : i.dataset.id}
+ output_dict[i.name] = {"id" : i.dataset.id, "src" : "hda"}
for i in self.output_library_datasets:
if i.dataset is not None:
- output_dict[i.name] = {"ldda_id" : i.dataset.id}
+ output_dict[i.name] = {"id" : i.dataset.id, "src" : "ldda"}
rval['outputs'] = output_dict
return rval
https://bitbucket.org/galaxy/galaxy-central/commits/f4272212f722/
Changeset: f4272212f722
Branch: search
User: Kyle Ellrott
Date: 2013-06-27 21:01:43
Summary: Removing stray print statement
Affected #: 1 file
diff -r 5f24b2c4f38bd65453cccad0b9bf526eff315918 -r f4272212f72244f5fb045b8d978dc140e7cfa7ca lib/galaxy/model/migrate/check.py
--- a/lib/galaxy/model/migrate/check.py
+++ b/lib/galaxy/model/migrate/check.py
@@ -44,7 +44,6 @@
# Let this go, it could possibly work with db's we don't support
log.error( "database_connection contains an unknown SQLAlchemy database dialect: %s" % dialect )
# Create engine and metadata
- print url, engine_options
engine = create_engine( url, **engine_options )
meta = MetaData( bind=engine )
# Try to load dataset table
https://bitbucket.org/galaxy/galaxy-central/commits/c2fb95ef8617/
Changeset: c2fb95ef8617
Branch: search
User: Kyle Ellrott
Date: 2013-06-27 22:37:14
Summary: Allowing zero length strings to be compared in the search conditions
Affected #: 1 file
diff -r f4272212f72244f5fb045b8d978dc140e7cfa7ca -r c2fb95ef8617cc8156ba936ee6d064ed098a8b9a lib/galaxy/model/search.py
--- a/lib/galaxy/model/search.py
+++ b/lib/galaxy/model/search.py
@@ -507,7 +507,7 @@
| '<=' -> '<='
| 'like' -> 'like'
)
-quote_word = "'" not_quote+:x "'" -> "".join(x)
+quote_word = "'" not_quote*:x "'" -> "".join(x)
not_quote = anything:x ?(x != "'") -> x
not_dquote = anything:x ?(x != '"') -> x
"""
https://bitbucket.org/galaxy/galaxy-central/commits/0b7b71c9d296/
Changeset: 0b7b71c9d296
Branch: search
User: Kyle Ellrott
Date: 2013-07-03 01:39:01
Summary: Adding in input_ldda field to job search
Affected #: 1 file
diff -r c2fb95ef8617cc8156ba936ee6d064ed098a8b9a -r 0b7b71c9d296c8ce92a41905f489d1a109e85f02 lib/galaxy/model/search.py
--- a/lib/galaxy/model/search.py
+++ b/lib/galaxy/model/search.py
@@ -418,6 +418,20 @@
)
)
+def job_input_ldda_filter(view, left, operator, right):
+ view.do_query = True
+ alias = aliased( JobToInputLibraryDatasetAssociation )
+ param_name = re.sub(r'^input_ldda.', '', left)
+ view.query = view.query.filter(
+ and_(
+ Job.id == alias.job_id,
+ alias.name == param_name,
+ alias.dataset_id == right
+ )
+ )
+
+
+
def job_output_hda_filter(view, left, operator, right):
view.do_query = True
alias = aliased( JobToOutputDatasetAssociation )
@@ -437,6 +451,7 @@
'tool_name' : ViewField('tool_name', sqlalchemy_field=Job.tool_id),
'state' : ViewField('state', sqlalchemy_field=Job.state),
'param' : ViewField('param', handler=job_param_filter),
+ 'input_ldda' : ViewField('input_ldda', handler=job_input_ldda_filter, id_decode=True),
'input_hda' : ViewField('input_hda', handler=job_input_hda_filter, id_decode=True),
'output_hda' : ViewField('output_hda', handler=job_output_hda_filter, id_decode=True)
}
https://bitbucket.org/galaxy/galaxy-central/commits/3b419687739b/
Changeset: 3b419687739b
Branch: search
User: Kyle Ellrott
Date: 2013-07-03 01:44:41
Summary: Adding missing import to search
Affected #: 1 file
diff -r 0b7b71c9d296c8ce92a41905f489d1a109e85f02 -r 3b419687739b3d4a759e73e99ff91633096bbbec lib/galaxy/model/search.py
--- a/lib/galaxy/model/search.py
+++ b/lib/galaxy/model/search.py
@@ -35,7 +35,7 @@
History, Library, LibraryFolder, LibraryDataset,StoredWorkflowTagAssociation,
StoredWorkflow, HistoryTagAssociation,HistoryDatasetAssociationTagAssociation,
ExtendedMetadata, ExtendedMetadataIndex, HistoryAnnotationAssociation, Job, JobParameter,
-JobToInputDatasetAssociation, JobToOutputDatasetAssociation, ToolVersion)
+JobToInputDatasetAssociation, JobToInputLibraryDatasetAssociation, JobToOutputDatasetAssociation, ToolVersion)
from galaxy.util.json import to_json_string
from sqlalchemy import and_
https://bitbucket.org/galaxy/galaxy-central/commits/df1b861724c2/
Changeset: df1b861724c2
Branch: search
User: Kyle Ellrott
Date: 2013-07-03 01:49:50
Summary: Fixing field name in selection statement
Affected #: 1 file
diff -r 3b419687739b3d4a759e73e99ff91633096bbbec -r df1b861724c205412a786cce00434dc39db391b1 lib/galaxy/model/search.py
--- a/lib/galaxy/model/search.py
+++ b/lib/galaxy/model/search.py
@@ -426,7 +426,7 @@
and_(
Job.id == alias.job_id,
alias.name == param_name,
- alias.dataset_id == right
+ alias.ldda_id == right
)
)
https://bitbucket.org/galaxy/galaxy-central/commits/74ad9ec46632/
Changeset: 74ad9ec46632
Branch: search
User: Kyle Ellrott
Date: 2013-07-18 23:46:32
Summary: Adding code to allow for search selection by 'copied_from_ldda_id' field
Affected #: 2 files
diff -r df1b861724c205412a786cce00434dc39db391b1 -r 74ad9ec46632d97d43f207098b80a824170bea58 lib/galaxy/model/__init__.py
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -1715,6 +1715,9 @@
misc_info = hda.info,
misc_blurb = hda.blurb )
+ if hda.copied_from_library_dataset_dataset_association is not None:
+ rval['copied_from_ldda_id'] = hda.copied_from_library_dataset_dataset_association.id
+
if hda.history is not None:
rval['history_id'] = hda.history.id
diff -r df1b861724c205412a786cce00434dc39db391b1 -r 74ad9ec46632d97d43f207098b80a824170bea58 lib/galaxy/model/search.py
--- a/lib/galaxy/model/search.py
+++ b/lib/galaxy/model/search.py
@@ -296,8 +296,11 @@
FIELDS = {
'name' : ViewField('name', sqlalchemy_field=HistoryDatasetAssociation.name),
'id' : ViewField('id',sqlalchemy_field=HistoryDatasetAssociation.id, id_decode=True),
- 'tag' : ViewField("tag", handler=history_dataset_handle_tag)
-
+ 'tag' : ViewField("tag", handler=history_dataset_handle_tag),
+ 'copied_from_ldda_id' : ViewField("copied_from_ldda_id",
+ sqlalchemy_field=HistoryDatasetAssociation.copied_from_library_dataset_dataset_association_id,
+ id_decode=True),
+ 'deleted' : ViewField('deleted', sqlalchemy_field=HistoryDatasetAssociation.deleted)
}
def search(self, trans):
https://bitbucket.org/galaxy/galaxy-central/commits/0e2c8d03786a/
Changeset: 0e2c8d03786a
Branch: search
User: kellrott
Date: 2013-08-05 01:59:14
Summary: Merging
Affected #: 1 file
diff -r 74ad9ec46632d97d43f207098b80a824170bea58 -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b lib/galaxy/model/search.py
--- a/lib/galaxy/model/search.py
+++ b/lib/galaxy/model/search.py
@@ -173,6 +173,7 @@
'id' : ViewField('id', sqlalchemy_field=LibraryDatasetDatasetAssociation.id, id_decode=True),
'deleted' : ViewField('deleted', sqlalchemy_field=LibraryDatasetDatasetAssociation.deleted),
'parent_library_id' : ViewField('parent_library_id', id_decode=True, post_filter=ldda_parent_library_filter),
+ 'data_type' : ViewField('data_type', sqlalchemy_field=LibraryDatasetDatasetAssociation.extension)
}
def search(self, trans):
https://bitbucket.org/galaxy/galaxy-central/commits/506d00954a3e/
Changeset: 506d00954a3e
Branch: search
User: Kyle Ellrott
Date: 2013-08-23 21:05:41
Summary: galaxy-central default merge and resolve
Affected #: 417 files
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af .coveragerc
--- /dev/null
+++ b/.coveragerc
@@ -0,0 +1,3 @@
+[run]
+branch = True
+include = lib/galaxy/*
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af .hgignore
--- a/.hgignore
+++ b/.hgignore
@@ -60,7 +60,7 @@
job_conf.xml
data_manager_conf.xml
shed_data_manager_conf.xml
-visualizations_conf.xml
+config/*
static/welcome.html.*
static/welcome.html
@@ -82,6 +82,10 @@
# Test output
run_functional_tests.html
test/tool_shed/tmp/*
+.coverage
+htmlcov
+run_unit_tests.html
+test/unit/**.log
# Project files
*.kpf
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af .hgtags
--- a/.hgtags
+++ b/.hgtags
@@ -3,3 +3,4 @@
75f09617abaadbc8cc732bb8ee519decaeb56ea7 release_2013.04.01
2cc8d10988e03257dc7b97f8bb332c7df745d1dd security_2013.04.08
524f246ca85395082719ae7a6ff72260d7ad5612 release_2013.06.03
+1ae95b3aa98d1ccf15b243ac3ce6a895eb7efc53 release_2013.08.12
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af README.txt
--- a/README.txt
+++ b/README.txt
@@ -7,7 +7,7 @@
HOW TO START
============
-Galaxy requires Python 2.5, 2.6 or 2.7. To check your python version, run:
+Galaxy requires Python 2.6 or 2.7. To check your python version, run:
% python -V
Python 2.7.3
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af buildbot_setup.sh
--- a/buildbot_setup.sh
+++ b/buildbot_setup.sh
@@ -65,6 +65,7 @@
"
SAMPLES="
+tool_conf.xml.sample
datatypes_conf.xml.sample
universe_wsgi.ini.sample
tool_data_table_conf.xml.sample
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af config/plugins/visualizations/README.txt
--- /dev/null
+++ b/config/plugins/visualizations/README.txt
@@ -0,0 +1,34 @@
+Custom visualization plugins
+----------------------------
+
+Visualizations can be added to your Galaxy instance by creating
+sub-directories, templates, and static files here.
+
+Properly configured and written visualizations will be accessible to
+the user when they click the 'visualizations' icon for a dataset
+in their history panel.
+
+The framework must be enabled in your 'universe_wsgi.ini' file by
+uncommenting (and having a valid path for) the
+'visualizations_plugin_directory' entry.
+
+For more information, see http://wiki.galaxyproject.org/VisualizationsRegistry
+
+
+Sub-directory structure
+-----------------------
+
+In general, sub-directories should follow the pattern:
+
+ my_visualization/
+ config/
+ my_visualization.xml
+ static/
+ ... any static files the visualization needs (if any)
+ templates/
+ ... any Mako templates the visualization needs
+
+The XML config file for a visualization plugin can be validated on the command
+line using (from your plugin directory):
+
+ xmllint my_visualization/config/my_visualization.xml --valid --noout
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af config/plugins/visualizations/circster/config/circster.xml
--- /dev/null
+++ b/config/plugins/visualizations/circster/config/circster.xml
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE visualization SYSTEM "../../visualization.dtd">
+<visualization name="circster">
+ <data_sources>
+ <data_source>
+ <model_class>HistoryDatasetAssociation</model_class>
+ <test type="isinstance" test_attr="datatype" result_type="datatype">data.Data</test>
+ <to_param param_attr="id">dataset_id</to_param>
+ <to_param assign="hda">hda_ldda</to_param>
+ </data_source>
+ <data_source>
+ <model_class>LibraryDatasetDatasetAssociation</model_class>
+ <test type="isinstance" test_attr="datatype" result_type="datatype">data.Data</test>
+ <to_param param_attr="id">dataset_id</to_param>
+ <to_param assign="ldda">hda_ldda</to_param>
+ </data_source>
+ </data_sources>
+ <params>
+ <param type="visualization">id</param>
+ <param type="hda_or_ldda">dataset_id</param>
+ <param_modifier type="string" modifies="dataset_id">hda_ldda</param_modifier>
+ <param type="dbkey">dbkey</param>
+ </params>
+ <!-- template_root and template are currently ignored for the 'built-in' visualizations -->
+ <template_root>webapps/galaxy/visualization</template_root>
+ <template>circster.mako</template>
+ <render_location>_top</render_location>
+</visualization>
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af config/plugins/visualizations/graphview/config/graphview.xml
--- /dev/null
+++ b/config/plugins/visualizations/graphview/config/graphview.xml
@@ -0,0 +1,20 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE visualization SYSTEM "../../visualization.dtd">
+<visualization name="Graphview">
+ <data_sources>
+ <data_source>
+ <model_class>HistoryDatasetAssociation</model_class>
+ <test type="has_dataprovider" test_attr="datatype">node-edge</test>
+ <to_param param_attr="id">dataset_id</to_param>
+ </data_source>
+ <data_source>
+ <model_class>HistoryDatasetAssociation</model_class>
+ <test type="isinstance" test_attr="datatype" result_type="datatype">graph.Rdf</test>
+ <to_param param_attr="id">dataset_id</to_param>
+ </data_source>
+ </data_sources>
+ <params>
+ <param type="dataset" var_name_in_template="hda" required="true">dataset_id</param>
+ </params>
+ <template>graphview/templates/graphview.mako</template>
+</visualization>
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af config/plugins/visualizations/graphview/static/graphview.css
--- /dev/null
+++ b/config/plugins/visualizations/graphview/static/graphview.css
@@ -0,0 +1,70 @@
+svg {
+ border: 1px solid lightgrey;
+ background-color: #FFF;
+ cursor: default;
+ -webkit-user-select: none;
+ -moz-user-select: none;
+ -ms-user-select: none;
+ -o-user-select: none;
+ user-select: none;
+}
+
+svg:not(.active):not(.ctrl) {
+ cursor: crosshair;
+}
+
+path.link {
+ fill: none;
+ stroke: #000;
+ stroke-width: 4px;
+ cursor: default;
+}
+
+svg:not(.active):not(.ctrl) path.link {
+ cursor: pointer;
+}
+
+path.link.selected {
+ stroke-dasharray: 10,2;
+}
+
+path.link.dragline {
+ pointer-events: none;
+}
+
+path.link.hidden {
+ stroke-width: 0;
+}
+
+circle.node {
+ stroke-width: 1.0px;
+ cursor: pointer;
+}
+
+circle.node.reflexive {
+ stroke: #000 !important;
+ stroke-width: 2.5px;
+}
+
+text {
+ font: 12px sans-serif;
+ pointer-events: none;
+}
+
+text.id {
+ text-anchor: middle;
+ font-weight: bold;
+}
+
+div.tooltip {
+ position: absolute;
+ text-align: center;
+ width: 60px;
+ height: 28px;
+ padding: 2px;
+ font: 12px sans-serif;
+ background: lightsteelblue;
+ border: 0px;
+ border-radius: 8px;
+ pointer-events: none;
+}
diff -r 0e2c8d03786a9bf22cde5f14da3e868dd4607e0b -r 506d00954a3eec4808ed8c0104b5e0404841b6af config/plugins/visualizations/graphview/static/graphview.js
--- /dev/null
+++ b/config/plugins/visualizations/graphview/static/graphview.js
@@ -0,0 +1,175 @@
+function get_firstChild(n) {
+ y=n.firstChild;
+ while (y && y.nodeType!=1) {
+ y=y.nextSibling;
+ }
+ return y;
+}
+
+function get_nextSibling(n) {
+ y=n.nextSibling;
+ while (y) {
+ if (y.nodeType==1) {
+ return y;
+ }
+ y=y.nextSibling;
+ }
+ return y;
+}
+
+function parse_xgmml_attr(elm) {
+ out = {};
+ var c = get_firstChild(elm);
+ while (c) {
+ if (c.nodeName == "att") {
+ if (c.attributes['type'].value == "string") {
+ out[c.attributes['name'].value] = c.attributes['value'].value;
+ }
+ }
+ c = get_nextSibling(c);
+ }
+ return out
+}
+
+function parse_xgmml(root, add_node, add_edge) {
+ graph=root.getElementsByTagName("graph")[0];
+ elm = get_firstChild(graph);
+ while (elm) {
+ if (elm.nodeName == "node") {
+ var attr = parse_xgmml_attr(elm);
+ add_node( elm.attributes['id'].value, elm.attributes['label'].value, attr );
+ }
+ if (elm.nodeName == "edge") {
+ var attr = parse_xgmml_attr(elm);
+ add_edge( elm.attributes['source'].value, elm.attributes['target'].value, attr );
+ }
+
+ elm = get_nextSibling(elm);
+ }
+}
+
+function parse_sif(data, add_node, add_edge) {
+ var lines = data.split("\n")
+ for (var i in lines) {
+ var tmp = lines[i].split("\t");
+ if (tmp.length == 3) {
+ add_edge(tmp[0], tmp[2], {type:tmp[1]});
+ }
+ }
+
+}
+
+jQuery.fn.graphViewer = function(config) {
+
+ var svg, colors;
+ var nodes = [],
+ links = [];
+
+ var height = config.height;
+ var width = config.width;
+
+
+ colors = d3.scale.category10();
+
+ this.each(function() {
+ svg = d3.select(this)
+ .append('svg')
+ .attr('width', width)
+ .attr('height', height);
+ }
+ );
+
+ var tooltip_div = d3.select("#tooltip").attr("class", "tooltip").style("opacity", 0);;
+
+ this.add_node = function(node_id, node_label, attr) {
+ nodes.push( {id: node_id, label:node_label, attr:attr} );
+ }
+
+ this.add_edge = function(src_id, dst_id, attr) {
+ var src, target;
+ for (var i in nodes) {
+ if (nodes[i].id == src_id) {
+ src = nodes[i];
+ }
+ if (nodes[i].id == dst_id) {
+ target = nodes[i];
+ }
+ }
+ if (typeof src==="undefined") {
+ i = nodes.length
+ nodes.push( {id:src_id, label:src_id, attr:{}} )
+ src = nodes[i]
+ }
+ if (typeof target==="undefined") {
+ i = nodes.length
+ nodes.push( {id:dst_id, label:dst_id, attr:{}} )
+ target = nodes[i]
+ }
+ if (src && target) {
+ links.push( {source: src, target: target, left: false, right: true } );
+ }
+ }
+
+ this.render = function() {
+ var path = svg.append('svg:g').selectAll('path'),
+ circle = svg.append('svg:g').selectAll('g');
+
+
+ circle = circle.data(nodes, function(d) { return d.id; });
+ var g = circle.enter().append('svg:g');
+
+ circle.on('mouseover', function(d) {
+ tooltip_div.transition()
+ .duration(200)
+ .style("opacity", .9);
+ tooltip_div.html( "<div>" + d.label + "</div><div>" + d.attr.type + "</div>" ).style("left", (d3.event.pageX + 40) + "px")
+ .style("top", (d3.event.pageY - 35) + "px");
+ })
+ .on("mouseout", function(d) {
+ tooltip_div.transition()
+ .duration(500)
+ .style("opacity", 0);
+ });
+
+ path = path.data(links);
+
+
+ function tick() {
+ path.attr('d', function(d) {
+ return 'M' + d.source.x + ',' + d.source.y + 'L' + d.target.x + ',' + d.target.y;
+ });
+ circle.attr('transform', function(d) {
+ return 'translate(' + d.x + ',' + d.y + ')';
+ });
+ }
+
+
+ g.append('svg:circle')
+ .attr('class', 'node')
+ .attr('r', 8)
+ .style('stroke', 'black')
+ .attr('fill', function(d) {
+ return colors(d['attr']['type'])
+ });
+
+ path.enter().append('svg:path')
+ .attr('class', 'link')
+
+
+ // init D3 force layout
+ var force = d3.layout.force()
+ .nodes(nodes)
+ .links(links)
+ .size([width, height])
+ .linkDistance(25)
+ .charge(-50)
+ .on('tick', tick)
+ circle.call(force.drag)
+ force.start()
+
+ }
+
+ return this
+
+}
+
This diff is so big that we needed to truncate the remainder.
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.
1
0
commit/galaxy-central: guerler: Use refreshHdas to refresh history during upload
by commits-noreply@bitbucket.org 22 Oct '13
by commits-noreply@bitbucket.org 22 Oct '13
22 Oct '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/82cd70ba007c/
Changeset: 82cd70ba007c
User: guerler
Date: 2013-10-22 04:00:42
Summary: Use refreshHdas to refresh history during upload
Affected #: 1 file
diff -r 8ae19975dd333c6b4b4c15f93a0350a24f3c10db -r 82cd70ba007ced10ee3f4e32486569641b83dc0a static/scripts/galaxy.upload.js
--- a/static/scripts/galaxy.upload.js
+++ b/static/scripts/galaxy.upload.js
@@ -278,7 +278,7 @@
sy.addClass(this.state.success);
// update galaxy history
- Galaxy.currHistoryPanel.refresh();
+ Galaxy.currHistoryPanel.refreshHdas();
},
// error
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.
1
0
2 new commits in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/2f0053f5952e/
Changeset: 2f0053f5952e
Branch: next-stable
User: jgoecks
Date: 2013-10-22 02:58:20
Summary: Fix track height calculation.
Affected #: 2 files
diff -r 3d138ced1f26c810a24bead0aa8fa6d8a65a7812 -r 2f0053f5952e9b93ded01fcd24ed87783dedc698 static/scripts/packed/viz/trackster/tracks.js
--- a/static/scripts/packed/viz/trackster/tracks.js
+++ b/static/scripts/packed/viz/trackster/tracks.js
@@ -1,1 +1,1 @@
-define(["libs/underscore","viz/visualization","viz/trackster/util","viz/trackster/slotting","viz/trackster/painters","viz/trackster/filters","mvc/data","mvc/tools"],function(ab,y,l,u,L,i,X,R){var q=ab.extend;var n={};var k=function(ac,ad){n[ac.attr("id")]=ad};var m=function(ac,ae,ag,af){ag=".group";var ad={};n[ac.attr("id")]=af;ac.bind("drag",{handle:"."+ae,relative:true},function(ao,ap){var an=$(this),at=$(this).parent(),ak=at.children(),am=n[$(this).attr("id")],aj,ai,aq,ah,al;ai=$(this).parents(ag);if(ai.length!==0){aq=ai.position().top;ah=aq+ai.outerHeight();var ar=n[ai.attr("id")];if(ap.offsetY<aq){$(this).insertBefore(ai);ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);ar.remove_drawable(am);ar.container.add_drawable(am);return}}}ai=null;for(al=0;al<ak.length;al++){aj=$(ak.get(al));aq=aj.position().top;ah=aq+aj.outerHeight();if(aj.is(ag)&&this!==aj.get(0)&&ap.offsetY>=aq&&ap.offsetY<=ah){if(ap.offsetY-aq<ah-ap.offsetY){aj.find(".content-div").prepend(this)}else{aj.find(".content-div").append(this)}if(am.container){am.container.remove_drawable(am)}n[aj.attr("id")].add_drawable(am);return}}for(al=0;al<ak.length;al++){aj=$(ak.get(al));if(ap.offsetY<aj.position().top&&!(aj.hasClass("reference-track")||aj.hasClass("intro"))){break}}if(al===ak.length){if(this!==ak.get(al-1)){at.append(this);n[at.attr("id")].move_drawable(am,al)}}else{if(this!==ak.get(al)){$(this).insertBefore(ak.get(al));n[at.attr("id")].move_drawable(am,(ap.deltaY>0?al-1:al))}}}).bind("dragstart",function(){ad["border-top"]=ac.css("border-top");ad["border-bottom"]=ac.css("border-bottom");$(this).css({"border-top":"1px solid blue","border-bottom":"1px solid blue"})}).bind("dragend",function(){$(this).css(ad)})};var F=20,B=100,I=12000,S=400,K=5000,x=100,o="Cannot display dataset due to an error. ",J="A converter for this dataset is not installed. Please check your datatypes_conf.xml file.",G="No data for this chrom/contig.",w="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",z="Tool cannot be rerun: ",b="Loading data...",U="Ready for display",Q=10,H=20,C=["Histogram","Line","Filled","Intensity"];function V(ad,ac){if(!ac){ac=0}var ae=Math.pow(10,ac);return Math.round(ad*ae)/ae}var r=function(ad,ac,af){if(!r.id_counter){r.id_counter=0}this.id=r.id_counter++;this.view=ad;this.container=ac;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.config=new j({params:this.config_params,onchange:this.config_onchange,saved_values:af.prefs});this.prefs=this.config.get("values");if(!this.prefs.name){this.prefs.name=af.name}if(this.config_onchange){this.config.on("change:values",this.config_onchange,this)}this.container_div=this.build_container_div();this.header_div=this.build_header_div();if(this.header_div){this.container_div.append(this.header_div);this.icons_div=$("<div/>").css("float","left").hide().appendTo(this.header_div);this.build_action_icons(this.action_icons_def);this.header_div.append($("<div style='clear: both'/>"));this.header_div.dblclick(function(ag){ag.stopPropagation()});var ae=this;this.container_div.hover(function(){ae.icons_div.show()},function(){ae.icons_div.hide()});$("<div style='clear: both'/>").appendTo(this.container_div)}};r.prototype.action_icons_def=[{name:"toggle_icon",title:"Hide/show content",css_class:"toggle",on_click_fn:function(ac){if(ac.prefs.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.prefs.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.prefs.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var ac=new a({model:ad.config});ac.render()}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".tooltip").remove();ac.remove()}}];q(r.prototype,{config_params:[{key:"name",label:"Name",type:"text",default_value:""},{key:"content_visible",type:"bool",default_value:true,hidden:true}],config_onchange:function(){this.track.set_name(this.track.config.get("values").name)},init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.prefs.content_visible){return true}return false},request_draw:function(){},_draw:function(ac){},to_dict:function(){},set_name:function(ac){this.old_name=this.prefs.name;this.prefs.name=ac;this.name_div.text(this.prefs.name)},revert_name:function(){if(this.old_name){this.prefs.name=this.old_name;this.name_div.text(this.prefs.name)}},remove:function(){this.changed();this.container.remove_drawable(this);var ac=this.view;this.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})},build_container_div:function(){},build_header_div:function(){},add_action_icon:function(ad,ai,ah,ag,ac,af){var ae=this;this.action_icons[ad]=$("<a/>").attr("title",ai).addClass("icon-button").addClass(ah).tooltip().click(function(){ag(ae)}).appendTo(this.icons_div);if(af){this.action_icons[ad].hide()}},build_action_icons:function(ac){var ae;for(var ad=0;ad<ac.length;ad++){ae=ac[ad];this.add_action_icon(ae.name,ae.title,ae.css_class,ae.on_click_fn,ae.prepend,ae.hide)}},update_icons:function(){},hide_contents:function(){},show_contents:function(){},get_drawables:function(){}});var A=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(A.prototype,r.prototype,{unpack_drawables:function(ae){this.drawables=[];var ad;for(var ac=0;ac<ae.length;ac++){ad=p(ae[ac],this.view,this);this.add_drawable(ad)}},init:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].init()}},_draw:function(ac){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad]._draw(ac)}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{prefs:this.prefs,obj_type:this.obj_type,drawables:ad}},add_drawable:function(ac){this.drawables.push(ac);ac.container=this;this.changed()},add_drawable_before:function(ae,ac){this.changed();var ad=this.drawables.indexOf(ac);if(ad!==-1){this.drawables.splice(ad,0,ae);return true}return false},replace_drawable:function(ae,ac,ad){var af=this.drawables.indexOf(ae);if(af!==-1){this.drawables[af]=ac;if(ad){ae.container_div.replaceWith(ac.container_div)}this.changed()}return af},remove_drawable:function(ad){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);ad.container=null;this.changed();return true}return false},move_drawable:function(ad,ae){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);this.drawables.splice(ae,0,ad);this.changed();return true}return false},get_drawables:function(){return this.drawables},get_tracks:function(af){var ac=this.drawables.slice(0),ad=[],ae;while(ac.length!==0){ae=ac.shift();if(ae instanceof af){ad.push(ae)}else{if(ae.drawables){ac=ac.concat(ae.drawables)}}}return ad}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});A.call(this,ad,ac,af);this.content_div=$("<div/>").addClass("content-div").attr("id","group_"+this.id+"_content_div").appendTo(this.container_div);k(this.container_div,this);k(this.content_div,this);m(this.container_div,this.drag_handle_class,".group",this);this.filters_manager=new i.FiltersManager(this);this.header_div.after(this.filters_manager.parent_div);this.saved_filters_managers=[];if("drawables" in af){this.unpack_drawables(af.drawables)}if("filters" in af){var ae=this.filters_manager;this.filters_manager=new i.FiltersManager(this,af.filters);ae.parent_div.replaceWith(this.filters_manager.parent_div);if(af.filters.visible){this.setup_multitrack_filtering()}}};q(P.prototype,r.prototype,A.prototype,{action_icons_def:[r.prototype.action_icons_def[0],r.prototype.action_icons_def[1],{name:"composite_icon",title:"Show composite track",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_composite_track()}},{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters();ac._restore_filter_managers()}else{ac.setup_multitrack_filtering();ac.request_draw({clear_tile_cache:true})}ac.filters_manager.toggle()}},r.prototype.action_icons_def[2]],build_container_div:function(){var ac=$("<div/>").addClass("group").attr("id","group_"+this.id);if(this.container){this.container.content_div.append(ac)}return ac},build_header_div:function(){var ac=$("<div/>").addClass("track-header");ac.append($("<div/>").addClass(this.drag_handle_class));this.name_div=$("<div/>").addClass("track-name").text(this.prefs.name).appendTo(ac);return ac},hide_contents:function(){this.tiles_div.hide()},show_contents:function(){this.tiles_div.show();this.request_draw()},update_icons:function(){var ae=this.drawables.length;if(ae===0){this.action_icons.composite_icon.hide();this.action_icons.filters_icon.hide()}else{if(ae===1){if(this.drawables[0] instanceof f){this.action_icons.composite_icon.show()}this.action_icons.filters_icon.hide()}else{var al,ak,ai,ao=true,ag=this.drawables[0].get_type(),ac=0;for(al=0;al<ae;al++){ai=this.drawables[al];if(ai.get_type()!==ag){can_composite=false;break}if(ai instanceof d){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".tooltip").remove()}if(ac>1&&ac===this.drawables.length){var ap={},ad;ai=this.drawables[0];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];ap[ad.name]=[ad]}for(al=1;al<this.drawables.length;al++){ai=this.drawables[al];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];if(ad.name in ap){ap[ad.name].push(ad)}}}this.filters_manager.remove_all();var af,ah,aj,am;for(var an in ap){af=ap[an];if(af.length===ac){ah=new i.NumberFilter({name:af[0].name,index:af[0].index});this.filters_manager.add_filter(ah)}}if(this.filters_manager.filters.length>0){this.action_icons.filters_icon.show()}else{this.action_icons.filters_icon.hide()}}else{this.action_icons.filters_icon.hide()}}}},_restore_filter_managers:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].filters_manager=this.saved_filters_managers[ac]}this.saved_filters_managers=[]},setup_multitrack_filtering:function(){if(this.filters_manager.filters.length>0){this.saved_filters_managers=[];for(var ac=0;ac<this.drawables.length;ac++){drawable=this.drawables[ac];this.saved_filters_managers.push(drawable.filters_manager);drawable.filters_manager=this.filters_manager}}this.filters_manager.init_filters()},show_composite_track:function(){var ad=new f(this.view,this.view,{name:this.prefs.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ad,true);ad.request_draw()},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){A.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(A.prototype.to_dict.call(this),{filters:this.filters_manager.to_dict()});if(this.filters_manager.visible()){this.setup_multitrack_filtering()}return ac},request_draw:function(ac){ab.each(this.drawables,function(ad){ad.request_draw(ac)})}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});A.call(this,"View",ac.container,ac);this.chrom=null;this.vis_id=ac.vis_id;this.dbkey=ac.dbkey;this.label_tracks=[];this.tracks_to_be_redrawn=[];this.max_low=0;this.max_high=0;this.zoom_factor=3;this.min_separation=30;this.has_changes=false;this.load_chroms_deferred=null;this.render();this.canvas_manager=new y.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new j({track:this,params:[{key:"a_color",label:"A Color",type:"color",default_value:"#FF0000"},{key:"c_color",label:"C Color",type:"color",default_value:"#00FF00"},{key:"g_color",label:"G Color",type:"color",default_value:"#0000FF"},{key:"t_color",label:"T Color",type:"color",default_value:"#FF00FF"},{key:"n_color",label:"N Color",type:"color",default_value:"#AAAAAA"}],saved_values:ac.prefs,onchange:function(){track.request_redraw({clear_tile_cache:true})}})},render:function(){this.requested_redraw=false;var ae=this.container,ac=this;this.top_container=$("<div/>").addClass("top-container").appendTo(ae);this.browser_content_div=$("<div/>").addClass("content").css("position","relative").appendTo(ae);this.bottom_container=$("<div/>").addClass("bottom-container").appendTo(ae);this.top_labeltrack=$("<div/>").addClass("top-labeltrack").appendTo(this.top_container);this.viewport_container=$("<div/>").addClass("viewport-container").attr("id","viewport-container").appendTo(this.browser_content_div);this.content_div=this.viewport_container;k(this.viewport_container,ac);this.intro_div=$("<div/>").addClass("intro").appendTo(this.viewport_container).hide();var af=$("<div/>").text("Add Datasets to Visualization").addClass("action-button").appendTo(this.intro_div).click(function(){y.select_datasets(galaxy_config.root+"visualization/list_current_history_datasets",galaxy_config.root+"api/datasets",{"f-dbkey":ac.dbkey},function(ag){ab.each(ag,function(ah){ac.add_drawable(p(ah,ac,ac))})})});this.nav_labeltrack=$("<div/>").addClass("nav-labeltrack").appendTo(this.bottom_container);this.nav_container=$("<div/>").addClass("trackster-nav-container").prependTo(this.top_container);this.nav=$("<div/>").addClass("trackster-nav").appendTo(this.nav_container);this.overview=$("<div/>").addClass("overview").appendTo(this.bottom_container);this.overview_viewport=$("<div/>").addClass("overview-viewport").appendTo(this.overview);this.overview_close=$("<a/>").attr("title","Close overview").addClass("icon-button overview-close tooltip").hide().appendTo(this.overview_viewport);this.overview_highlight=$("<div/>").addClass("overview-highlight").hide().appendTo(this.overview_viewport);this.overview_box_background=$("<div/>").addClass("overview-boxback").appendTo(this.overview_viewport);this.overview_box=$("<div/>").addClass("overview-box").appendTo(this.overview_viewport);this.default_overview_height=this.overview_box.height();this.nav_controls=$("<div/>").addClass("nav-controls").appendTo(this.nav);this.chrom_select=$("<select/>").attr({name:"chrom"}).css("width","15em").append("<option value=''>Loading</option>").appendTo(this.nav_controls);var ad=function(ag){if(ag.type==="focusout"||(ag.keyCode||ag.which)===13||(ag.keyCode||ag.which)===27){if((ag.keyCode||ag.which)!==27){ac.go_to($(this).val())}$(this).hide();$(this).val("");ac.location_span.show();ac.chrom_select.show()}};this.nav_input=$("<input/>").addClass("nav-input").hide().bind("keyup focusout",ad).appendTo(this.nav_controls);this.location_span=$("<span/>").addClass("location").attr("original-title","Click to change location").tooltip({placement:"bottom"}).appendTo(this.nav_controls);this.location_span.click(function(){ac.location_span.hide();ac.chrom_select.hide();ac.nav_input.val(ac.chrom+":"+ac.low+"-"+ac.high);ac.nav_input.css("display","inline-block");ac.nav_input.select();ac.nav_input.focus();ac.nav_input.autocomplete({source:function(ai,ag){var aj=[],ah=$.map(ac.get_tracks(d),function(ak){return ak.data_manager.search_features(ai.term).success(function(al){aj=aj.concat(al)})});$.when.apply($,ah).done(function(){ag($.map(aj,function(ak){return{label:ak[0],value:ak[1]}}))})}})});if(this.vis_id!==undefined){this.hidden_input=$("<input/>").attr("type","hidden").val(this.vis_id).appendTo(this.nav_controls)}this.zo_link=$("<a/>").attr("id","zoom-out").attr("title","Zoom out").tooltip({placement:"bottom"}).click(function(){ac.zoom_out();ac.request_redraw()}).appendTo(this.nav_controls);this.zi_link=$("<a/>").attr("id","zoom-in").attr("title","Zoom in").tooltip({placement:"bottom"}).click(function(){ac.zoom_in();ac.request_redraw()}).appendTo(this.nav_controls);this.load_chroms_deferred=this.load_chroms({low:0});this.chrom_select.bind("change",function(){ac.change_chrom(ac.chrom_select.val())});this.browser_content_div.click(function(ag){$(this).find("input").trigger("blur")});this.browser_content_div.bind("dblclick",function(ag){ac.zoom_in(ag.pageX,this.viewport_container)});this.overview_box.bind("dragstart",function(ag,ah){this.current_x=ah.offsetX}).bind("drag",function(ag,ai){var aj=ai.offsetX-this.current_x;this.current_x=ai.offsetX;var ah=Math.round(aj/ac.viewport_container.width()*(ac.max_high-ac.max_low));ac.move_delta(-ah)});this.overview_close.click(function(){ac.reset_overview()});this.viewport_container.bind("draginit",function(ag,ah){if(ag.clientX>ac.viewport_container.width()-16){return false}}).bind("dragstart",function(ag,ah){ah.original_low=ac.low;ah.current_height=ag.clientY;ah.current_x=ah.offsetX}).bind("drag",function(ai,ak){var ag=$(this);var al=ak.offsetX-ak.current_x;var ah=ag.scrollTop()-(ai.clientY-ak.current_height);ag.scrollTop(ah);ak.current_height=ai.clientY;ak.current_x=ak.offsetX;var aj=Math.round(al/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}).bind("mousewheel",function(ai,ak,ah,ag){if(ah){ah*=50;var aj=Math.round(-ah/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}});this.top_labeltrack.bind("dragstart",function(ag,ah){return $("<div />").css({height:ac.browser_content_div.height()+ac.top_labeltrack.height()+ac.nav_labeltrack.height()+1,top:"0px",position:"absolute","background-color":"#ccf",opacity:0.5,"z-index":1000}).appendTo($(this))}).bind("drag",function(ak,al){$(al.proxy).css({left:Math.min(ak.pageX,al.startX)-ac.container.offset().left,width:Math.abs(ak.pageX-al.startX)});var ah=Math.min(ak.pageX,al.startX)-ac.container.offset().left,ag=Math.max(ak.pageX,al.startX)-ac.container.offset().left,aj=(ac.high-ac.low),ai=ac.viewport_container.width();ac.update_location(Math.round(ah/ai*aj)+ac.low,Math.round(ag/ai*aj)+ac.low)}).bind("dragend",function(al,am){var ah=Math.min(al.pageX,am.startX),ag=Math.max(al.pageX,am.startX),aj=(ac.high-ac.low),ai=ac.viewport_container.width(),ak=ac.low;ac.low=Math.round(ah/ai*aj)+ak;ac.high=Math.round(ag/ai*aj)+ak;$(am.proxy).remove();ac.request_redraw()});this.add_label_track(new W(this,{content_div:this.top_labeltrack}));this.add_label_track(new W(this,{content_div:this.nav_labeltrack}));$(window).bind("resize",function(){if(this.resize_timer){clearTimeout(this.resize_timer)}this.resize_timer=setTimeout(function(){ac.resize_window()},500)});$(document).bind("redraw",function(){ac.redraw()});this.reset();$(window).trigger("resize")},get_base_color:function(ac){return this.config.get("values")[ac.toLowerCase()+"_color"]||this.config.get("values").n_color}});q(Y.prototype,A.prototype,{changed:function(){this.has_changes=true},update_intro_div:function(){if(this.drawables.length===0){this.intro_div.show()}else{this.intro_div.hide()}},trigger_navigate:function(ad,af,ac,ag){if(this.timer){clearTimeout(this.timer)}if(ag){var ae=this;this.timer=setTimeout(function(){ae.trigger("navigate",ad+":"+af+"-"+ac)},500)}else{view.trigger("navigate",ad+":"+af+"-"+ac)}},update_location:function(ac,ae){this.location_span.text(commatize(ac)+" - "+commatize(ae));this.nav_input.val(this.chrom+":"+commatize(ac)+"-"+commatize(ae));var ad=view.chrom_select.val();if(ad!==""){this.trigger_navigate(ad,view.low,view.high,true)}},load_chroms:function(ae){ae.num=x;var ac=this,ad=$.Deferred();$.ajax({url:galaxy_config.root+"api/genomes/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){var ah=new D(ac);ac.add_label_track(ah);ac.reference_track=ah}ac.chrom_data=ag.chrom_info;var ak='<option value="">Select Chrom/Contig</option>';for(var aj=0,af=ac.chrom_data.length;aj<af;aj++){var ai=ac.chrom_data[aj].chrom;ak+='<option value="'+ai+'">'+ai+"</option>"}if(ag.prev_chroms){ak+='<option value="previous">Previous '+x+"</option>"}if(ag.next_chroms){ak+='<option value="next">Next '+x+"</option>"}ac.chrom_select.html(ak);ac.chrom_start_index=ag.start_index;ad.resolve(ag.chrom_info)},error:function(){alert("Could not load chroms for this dbkey:",ac.dbkey)}});return ad},change_chrom:function(ah,ad,aj){var ae=this;if(!ae.chrom_data){ae.load_chroms_deferred.then(function(){ae.change_chrom(ah,ad,aj)});return}if(!ah||ah==="None"){return}if(ah==="previous"){ae.load_chroms({low:this.chrom_start_index-x});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+x});return}var ai=$.grep(ae.chrom_data,function(ak,al){return ak.chrom===ah})[0];if(ai===undefined){ae.load_chroms({chrom:ah},function(){ae.change_chrom(ah,ad,aj)});return}else{if(ah!==ae.chrom){ae.chrom=ah;ae.chrom_select.val(ae.chrom);ae.max_high=ai.len-1;ae.reset();for(var ag=0,ac=ae.drawables.length;ag<ac;ag++){var af=ae.drawables[ag];if(af.init){af.init()}}if(ae.reference_track){ae.reference_track.init()}}if(ad&&aj){ae.low=Math.max(ad,0);ae.high=Math.min(aj,ae.max_high)}else{ae.low=0;ae.high=ae.max_high}ae.reset_overview();ae.request_redraw()}},go_to:function(ag){ag=ag.replace(/,/g,"");ag=ag.replace(/:|\-/g," ");var ad=ag.split(/\s+/),af=ad[0],ae=(ad[1]?parseInt(ad[1],10):null),ac=(ad[2]?parseInt(ad[2],10):null);if(!ac){ae=ae-15;ac=ae+15}this.change_chrom(af,ae,ac)},move_fraction:function(ae){var ac=this;var ad=ac.high-ac.low;this.move_delta(ae*ad)},move_delta:function(af){var ac=this;var ae=ac.high-ac.low;if(ac.low-af<ac.max_low){ac.low=ac.max_low;ac.high=ac.max_low+ae}else{if(ac.high-af>ac.max_high){ac.high=ac.max_high;ac.low=ac.max_high-ae}else{ac.high-=af;ac.low-=af}}ac.request_redraw({data_fetch:false});if(this.redraw_on_move_fn){clearTimeout(this.redraw_on_move_fn)}this.redraw_on_move_fn=setTimeout(function(){ac.request_redraw()},200);var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);ac.init();this.changed();this.update_intro_div()},add_label_track:function(ac){ac.view=this;ac.init();this.label_tracks.push(ac)},remove_drawable:function(ae,ad){A.prototype.remove_drawable.call(this,ae);if(ad){var ac=this;ae.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})}},reset:function(){this.low=this.max_low;this.high=this.max_high;this.viewport_container.find(".yaxislabel").remove()},request_redraw:function(ad,ae){var ac=this,af=(ae?[ae]:ac.drawables);ab.each(af,function(ag){var ah=ab.find(ac.tracks_to_be_redrawn,function(ai){return ai[0]===ag});if(ah){ah[1]=ad}else{ac.tracks_to_be_redrawn.push([ag,ad])}});if(!this.requested_redraw){requestAnimationFrame(function(){ac._redraw()});this.requested_redraw=true}},_redraw:function(){this.requested_redraw=false;var ac=this.low,ag=this.high;if(ac<this.max_low){ac=this.max_low}if(ag>this.max_high){ag=this.max_high}var ad=this.high-this.low;if(this.high!==0&&ad<this.min_separation){ag=ac+this.min_separation}this.low=Math.floor(ac);this.high=Math.ceil(ag);this.update_location(this.low,this.high);this.resolution_px_b=this.viewport_container.width()/(this.high-this.low);var af=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ah=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ae=13;this.overview_box.css({left:af,width:Math.max(ae,ah)}).show();if(ah<ae){this.overview_box.css("left",af-(ae-ah)/2)}if(this.overview_highlight){this.overview_highlight.css({left:af,width:ah})}ab.each(this.tracks_to_be_redrawn,function(ak){var ai=ak[0],aj=ak[1];if(ai){ai._draw(aj)}});this.tracks_to_be_redrawn=[];ab.each(this.label_tracks,function(ai){ai._draw()})},zoom_in:function(ad,ae){if(this.max_high===0||this.high-this.low<=this.min_separation){return}var af=this.high-this.low,ag=af/2+this.low,ac=(af/this.zoom_factor)/2;if(ad){ag=ad/this.viewport_container.width()*(this.high-this.low)+this.low}this.low=Math.round(ag-ac);this.high=Math.round(ag+ac);this.changed();this.request_redraw()},zoom_out:function(){if(this.max_high===0){return}var ad=this.high-this.low,ae=ad/2+this.low,ac=(ad*this.zoom_factor)/2;this.low=Math.round(ae-ac);this.high=Math.round(ae+ac);this.changed();this.request_redraw()},resize_window:function(){this.viewport_container.height(this.container.height()-this.top_container.height()-this.bottom_container.height());this.request_redraw()},set_overview:function(ae){if(this.overview_drawable){if(this.overview_drawable.dataset.id===ae.dataset.id){return}this.overview_viewport.find(".track").remove()}var ad=ae.copy({content_div:this.overview_viewport}),ac=this;ad.header_div.hide();ad.is_overview=true;ac.overview_drawable=ad;this.overview_drawable.postdraw_actions=function(){ac.overview_highlight.show().height(ac.overview_drawable.content_div.height());ac.overview_viewport.height(ac.overview_drawable.content_div.height()+ac.overview_box.outerHeight());ac.overview_close.show();ac.resize_window()};ac.overview_drawable.request_draw();this.changed()},reset_overview:function(){$(".tooltip").remove();this.overview_viewport.find(".track-tile").remove();this.overview_viewport.height(this.default_overview_height);this.overview_box.height(this.default_overview_height);this.overview_close.hide();this.overview_highlight.hide();view.resize_window();view.overview_drawable=null}});var s=R.Tool.extend({defaults:{track:null},initialize:function(ac){if(ac.tool_state!==undefined){this.set("hidden",ac.tool_state.hidden)}this.remove_inputs(["data","hidden_data","conditional"])},state_dict:function(ac){return ab.extend(this.get_inputs_dict(),{hidden:!this.is_visible()})}});var v=Backbone.View.extend({events:{"change input":"update_value"},render:function(){var ae=this.$el.addClass("param-row"),af=this.model;var ac=$("<div>").addClass("param-label").text(af.get("label")).appendTo(ae);var ad=$("<div/>").addClass("param-input").html(af.get("html")).appendTo(ae);ad.find(":input").val(af.get("value"));$("<div style='clear: both;'/>").appendTo(ae)},update_value:function(ac){this.model.set_value($(ac.target).val())}});var aa=Backbone.View.extend({initialize:function(ac){this.model.on("change:hidden",this.set_visible,this)},render:function(){var ad=this;tool=this.model,parent_div=this.$el.addClass("dynamic-tool").hide();parent_div.bind("drag",function(ah){ah.stopPropagation()}).click(function(ah){ah.stopPropagation()}).bind("dblclick",function(ah){ah.stopPropagation()}).keydown(function(ah){ah.stopPropagation()});var ae=$("<div class='tool-name'>").appendTo(parent_div).text(tool.get("name"));tool.get("inputs").each(function(ai){var ah=new v({model:ai});ah.render();parent_div.append(ah.$el)});parent_div.find("input").click(function(){$(this).select()});var af=$("<div>").addClass("param-row").appendTo(parent_div);var ag=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(af);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(af);ac.click(function(){ad.run_on_region()});ag.click(function(){ad.run_on_dataset()});if(tool.is_visible()){this.$el.show()}},set_visible:function(){if(this.model.is_visible()){this.$el.show()}else{this.$el.hide()}},update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},run_on_dataset:function(){var ac=this.model;this.run({target_dataset_id:this.model.get("track").dataset.id,action:"rerun",tool_id:ac.id},null,function(ad){Galaxy.modal.show({title:ac.get("name")+" is Running",body:ac.get("name")+" is running on the complete dataset. Tool outputs are in dataset's history.",buttons:{Close:function(){Galaxy.modal.hide()}}})})},run_on_region:function(){var ad=this.model.get("track"),ag=this.model,ai=new y.GenomeRegion({chrom:ad.view.chrom,start:ad.view.low,end:ad.view.high}),aj={target_dataset_id:ad.dataset.id,action:"rerun",tool_id:ag.id,regions:[ai.toJSON()]},ah=ad,al=aj.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ak=new P(view,view,{name:this.prefs.name});var af=ah.container.replace_drawable(ah,ak,false);ak.container_div.insertBefore(ah.view.content_div.children()[af]);ak.add_drawable(ah);ah.container_div.appendTo(ak.content_div);ac=ak}else{ac=ah.container}var ae=new ah.constructor(view,ac,{name:al,hda_ldda:"hda"});ae.init_for_tool_data();ae.change_mode(ah.mode);ae.set_filters_manager(ah.filters_manager.copy(ae));ae.update_icons();ac.add_drawable(ae);ae.tiles_div.text("Starting job.");this.run(aj,ae,function(am){ae.set_dataset(new X.Dataset(am));ae.tiles_div.text("Running job.");ae.init()})},run:function(ac,ae,af){ac.inputs=this.model.get_inputs_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_config.root+"api/tools",data:JSON.stringify(ac),dataType:"json",contentType:"application/json",type:"POST"},interval:2000,success_fn:function(ag){return ag!=="pending"}});$.when(ad.go()).then(function(ag){if(ag==="no converter"){ae.container_div.addClass("error");ae.content_div.text(J)}else{if(ag.error){ae.container_div.addClass("error");ae.content_div.text(z+ag.message)}else{af(ag)}}})}});var E=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};E.prototype.gen_val=function(ac){if(this.filter.high===Number.MAX_VALUE||this.filter.low===-Number.MAX_VALUE||this.filter.low===this.filter.high){return this.default_val}return((parseFloat(ac[this.filter.index])-this.filter.low)/(this.filter.high-this.filter.low))};var j=Backbone.Model.extend({initialize:function(ad){var ac={};ab.each(ad.params,function(ae){ac[ae.key]=ae.default_value});if(ad.saved_values){ab.each(this.get("params"),function(ae){if(ae.key in ad.saved_values){ac[ae.key]=ad.saved_values[ae.key]}})}this.set("values",ac)},set_param_default_value:function(ad,ac){var ae=ab.find(this.get("params"),function(af){return af.key===ad});if(ae){ae.default_value=ac}},set_param_value:function(ac,ad){var ae=ab.find(this.get("params"),function(af){return af.key===ac});if(ae){if(typeof ad==="string"||ad instanceof String){if(ad.trim()===""){ad=ae.default_value}else{if(ae.type==="float"){ad=parseFloat(ad)}else{if(ae.type==="int"){ad=parseInt(ad,10)}}}}}if(this.get("values")[ac]!==ad){this.get("values")[ac]=ad;this.trigger("change:values");return true}else{return false}}});var a=Backbone.View.extend({render:function(){var aj=this.model;var ac=$("<div/>").keydown(function(ak){ak.stopPropagation()});var ai;function ah(ao,ak){for(var at=0;at<ao.length;at++){ai=ao[at];if(ai.hidden){continue}var am="param_"+at;var ax=aj.get("values")[ai.key];var az=$("<div class='form-row' />").appendTo(ak);az.append($("<label />").attr("for",am).text(ai.label+":"));if(ai.type==="bool"){az.append($('<input type="checkbox" />').attr("id",am).attr("name",am).attr("checked",ax))}else{if(ai.type==="text"){az.append($('<input type="text"/>').attr("id",am).val(ax).click(function(){$(this).select()}))}else{if(ai.type==="select"){var av=$("<select />").attr("id",am);for(var aq=0;aq<ai.options.length;aq++){$("<option/>").text(ai.options[aq].label).attr("value",ai.options[aq].value).appendTo(av)}av.val(ax);az.append(av)}else{if(ai.type==="color"){var ay=$("<div/>").appendTo(az),au=$("<input />").attr("id",am).attr("name",am).val(ax).css("float","left").appendTo(ay).click(function(aB){$(".tooltip").removeClass("in");var aA=$(this).siblings(".tooltip").addClass("in");aA.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top+Galaxy.modal.scrollTop()-($(aA).height()/2)+($(this).height()/2)}).show();aA.click(function(aC){aC.stopPropagation()});$(document).bind("click.color-picker",function(){aA.hide();$(document).unbind("click.color-picker")});aB.stopPropagation()}),ar=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(ay).attr("title","Set new random color").tooltip(),aw=$("<div class='tooltip right' style='position: absolute;' />").appendTo(ay).hide(),an=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(aw),al=$("<div class='tooltip-arrow'></div>").appendTo(aw),ap=$.farbtastic(an,{width:100,height:100,callback:au,color:ax});ay.append($("<div/>").css("clear","both"));(function(aA){ar.click(function(){aA.setColor(l.get_random_color())})})(ap)}else{az.append($("<input />").attr("id",am).attr("name",am).val(ax))}}}}if(ai.help){az.append($("<div class='help'/>").text(ai.help))}}}ah(aj.get("params"),ac);var ad=this,ag=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ae=function(){ad.update_from_form($(Galaxy.modal.el));Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},af=function(ak){if((ak.keyCode||ak.which)===27){ag()}else{if((ak.keyCode||ak.which)===13){ae()}}};$(window).bind("keypress.check_enter_esc",af);Galaxy.modal.show({title:"Configure",body:ac,buttons:{Cancel:ag,Ok:ae}})},update_from_form:function(ac){var ad=this.model;var ae=false;ab.each(ad.get("params"),function(ah,af){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}ae=ad.set_param_value(ah.key,ag)||ae}})}});var c=function(ac,af,ag,ad,ae){this.track=ac;this.region=af;this.low=af.get("start");this.high=af.get("end");this.w_scale=ag;this.canvas=ad;this.html_elt=$("<div class='track-tile'/>").append(ad);this.data=ae;this.stale=false};c.prototype.predisplay_actions=function(){};var M=function(ac,af,ag,ad,ae){c.call(this,ac,af,ag,ad,ae)};M.prototype.predisplay_actions=function(){};var O=function(af,am,ao,ae,ah,ai,ap,ad,al){c.call(this,af,am,ao,ae,ah);this.mode=ai;this.all_slotted=ad;this.feature_mapper=al;this.has_icons=false;if(ap){this.has_icons=true;var aj=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:F,width:ae.width}).prependTo(this.html_elt);var ak=new y.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),an=ah.length,ag=$("<a/>").addClass("icon more-down").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a/>").addClass("icon more-across").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ag.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.DEEP_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()});ac.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.BROAD_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()})}};q(O.prototype,c.prototype);O.prototype.predisplay_actions=function(){var ad=this,ac={};if(ad.mode!=="Pack"){return}$(this.html_elt).hover(function(){this.hovered=true;$(this).mousemove()},function(){this.hovered=false;$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()}).mousemove(function(ao){if(!this.hovered){return}var aj=$(this).offset(),an=ao.pageX-aj.left,am=ao.pageY-aj.top,at=ad.feature_mapper.get_feature_data(an,am),ak=(at?at[0]:null);$(this).parents(".track-content").children(".overlay").children(".feature-popup").each(function(){if(!ak||$(this).attr("id")!==ak.toString()){$(this).remove()}});if(at){var af=ac[ak];if(!af){var ap={name:at[3],start:at[1],end:at[2],strand:at[4]},ai=ad.track.filters_manager.filters,ah;for(var al=0;al<ai.length;al++){ah=ai[al];ap[ah.name]=at[ah.index]}af=$("<div/>").attr("id",ak).addClass("feature-popup");var au=$("<table/>"),ar,aq,av;for(ar in ap){aq=ap[ar];av=$("<tr/>").appendTo(au);$("<th/>").appendTo(av).text(ar);$("<td/>").attr("align","left").appendTo(av).text(typeof(aq)==="number"?V(aq,2):aq)}af.append($("<div class='feature-popup-inner'>").append(au));ac[ak]=af}af.appendTo($(this).parents(".track-content").children(".overlay"));var ag=an+parseInt(ad.html_elt.css("left"),10)-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"),10)+7;af.css("left",ag+"px").css("top",ae+"px")}else{if(!ao.isPropagationStopped()){ao.stopPropagation();$(this).siblings().each(function(){$(this).trigger(ao)})}}}).mouseleave(function(){$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()})};var g=function(ad,ac,ae){q(ae,{drag_handle_class:"draghandle"});r.call(this,ad,ac,ae);this.dataset=null;if(ae.dataset){this.dataset=(ae.dataset instanceof Backbone.Model?ae.dataset:X.Dataset.findOrCreate(ae.dataset))}this.dataset_check_type="converted_datasets_state";this.data_url_extra_params={};this.data_query_wait=("data_query_wait" in ae?ae.data_query_wait:K);this.data_manager=("data_manager" in ae?ae.data_manager:new y.GenomeDataManager({dataset:this.dataset,genome:new y.Genome({key:ad.dbkey,chroms_info:{chrom_info:ad.chrom_data}}),data_mode_compatible:this.data_and_mode_compatible,can_subset:this.can_subset}));this.min_height_px=16;this.max_height_px=800;this.visible_height_px=this.prefs.height;this.content_div=$("<div class='track-content'>").appendTo(this.container_div);if(this.container){this.container.content_div.append(this.container_div);if(!("resize" in ae)||ae.resize){this.add_resize_handle()}}};q(g.prototype,r.prototype,{action_icons_def:[{name:"mode_icon",title:"Set display mode",css_class:"chevron-expand",on_click_fn:function(){}},r.prototype.action_icons_def[0],{name:"overview_icon",title:"Set as overview",css_class:"overview-icon",on_click_fn:function(ac){ac.view.set_overview(ac)}},r.prototype.action_icons_def[1],{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters()}else{ac.filters_manager.init_filters()}ac.filters_manager.toggle()}},{name:"tools_icon",title:"Tool",css_class:"hammer",on_click_fn:function(ac){ac.tool.toggle();if(ac.tool.is_visible()){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".tooltip").remove()}},{name:"param_space_viz_icon",title:"Tool parameter space visualization",css_class:"arrow-split",on_click_fn:function(ac){var af='<strong>Tool</strong>: <%= track.tool.name %><br/><strong>Dataset</strong>: <%= track.name %><br/><strong>Region(s)</strong>: <select name="regions"><option value="cur">current viewing area</option><option value="bookmarks">bookmarks</option><option value="both">current viewing area and bookmarks</option></select>',ae=ab.template(af,{track:ac});var ah=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new y.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new y.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}Galaxy.modal.hide();window.location.href=galaxy_config.root+"visualization/sweepster?"+$.param({dataset_id:ac.dataset.id,hda_ldda:ac.dataset.get("hda_ldda"),regions:JSON.stringify(new Backbone.Collection(al).toJSON())})},ag=function(ai){if((ai.keyCode||ai.which)===27){ah()}else{if((ai.keyCode||ai.which)===13){ad()}}};Galaxy.modal.show({title:"Visualize tool parameter space and output from different parameter settings?",body:ae,buttons:{No:ah,Yes:ad}})}},r.prototype.action_icons_def[2]],can_draw:function(){return this.dataset&&r.prototype.can_draw.call(this)},build_container_div:function(){return $("<div/>").addClass("track").attr("id","track_"+this.id).css("position","relative")},build_header_div:function(){var ac=$("<div class='track-header'/>");if(this.view.editor){this.drag_div=$("<div/>").addClass(this.drag_handle_class).appendTo(ac)}this.name_div=$("<div/>").addClass("track-name").appendTo(ac).text(this.prefs.name).attr("id",this.prefs.name.replace(/\s+/g,"-").replace(/[^a-zA-Z0-9\-]/g,"").toLowerCase());return ac},set_dataset:function(ac){this.dataset=ac;this.data_manager.set("dataset",ac)},on_resize:function(){this.request_draw({clear_tile_cache:true})},add_resize_handle:function(){var ac=this;var af=false;var ae=false;var ad=$("<div class='track-resize'>");$(ac.container_div).hover(function(){if(ac.prefs.content_visible){af=true;ad.show()}},function(){af=false;if(!ae){ad.hide()}});ad.hide().bind("dragstart",function(ag,ah){ae=true;ah.original_height=$(ac.content_div).height()}).bind("drag",function(ah,ai){var ag=Math.min(Math.max(ai.original_height+ai.deltaY,ac.min_height_px),ac.max_height_px);$(ac.tiles_div).css("height",ag);ac.visible_height_px=(ac.max_height_px===ag?0:ag);ac.on_resize()}).bind("dragend",function(ag,ah){ac.tile_cache.clear();ae=false;if(!af){ad.hide()}ac.config.get("values").height=ac.visible_height_px;ac.changed()}).appendTo(ac.container_div)},set_display_modes:function(af,ai){this.display_modes=af;this.mode=(ai?ai:(this.config&&this.config.get("values").mode?this.config.get("values").mode:this.display_modes[0]));this.action_icons.mode_icon.attr("title","Set display mode (now: "+this.mode+")");var ad=this,ag={};for(var ae=0,ac=ad.display_modes.length;ae<ac;ae++){var ah=ad.display_modes[ae];ag[ah]=function(aj){return function(){ad.change_mode(aj);ad.icons_div.show();ad.container_div.mouseleave(function(){ad.icons_div.hide()})}}(ah)}make_popupmenu(this.action_icons.mode_icon,ag)},build_action_icons:function(){r.prototype.build_action_icons.call(this,this.action_icons_def);if(this.display_modes!==undefined){this.set_display_modes(this.display_modes)}},hide_contents:function(){this.tiles_div.hide();this.container_div.find(".yaxislabel, .track-resize").hide()},show_contents:function(){this.tiles_div.show();this.container_div.find(".yaxislabel, .track-resize").show();this.request_draw()},get_type:function(){if(this instanceof W){return"LabelTrack"}else{if(this instanceof D){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof T){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof d){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.tiles_div.css("height","auto");ad.tiles_div.text("").children().remove();ad.container_div.removeClass("nodata error pending");if(!ad.dataset.id){return}var ac=$.Deferred(),af={hda_ldda:ad.dataset.get("hda_ldda"),data_type:this.dataset_check_type,chrom:ad.view.chrom,retry:ae};$.getJSON(this.dataset.url(),af,function(ag){if(!ag||ag==="error"||ag.kind==="error"){ad.container_div.addClass("error");ad.tiles_div.text(o);if(ag.message){ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("View error").click(function(){Galaxy.modal.show({title:"Trackster Error",body:"<pre>"+ag.message+"</pre>",buttons:{Close:function(){Galaxy.modal.hide()}}})}));ad.tiles_div.append($("<span/>").text(" "));ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("Try again").click(function(){ad.init(true)}))}}else{if(ag==="no converter"){ad.container_div.addClass("error");ad.tiles_div.text(J)}else{if(ag==="no data"||(ag.data!==undefined&&(ag.data===null||ag.data.length===0))){ad.container_div.addClass("nodata");ad.tiles_div.text(G)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(w);setTimeout(function(){ad.init()},ad.data_query_wait)}else{if(ag==="data"||ag.status==="data"){if(ag.valid_chroms){ad.valid_chroms=ag.valid_chroms;ad.update_icons()}ad.tiles_div.text(U);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when.apply($,ad.predraw_init()).done(function(){ac.resolve();ad.container_div.removeClass("nodata error pending");ad.request_draw()})}else{ac.resolve()}}}}}}});this.update_icons();return ac},predraw_init:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){ac.container_div.addClass("line-track");var af=ad.data;if(af&&af.min&&af.max){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.config.set_param_default_value("min_value",ae);ac.config.set_param_default_value("max_value",ag);ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},get_drawables:function(){return this}});var N=function(ae,ad,ag){g.call(this,ae,ad,ag);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in ag?ag.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=(ag.tool?new s(ab.extend(ag.tool,{track:this,tool_state:ag.tool_state})):null);this.tile_cache=new y.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){var af=new aa({model:this.tool});af.render();this.dynamic_tool_div=af.$el;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);if(!this.prefs.content_visible){this.tiles_div.hide()}this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(ag.mode){this.change_mode(ag.mode)}};q(N.prototype,r.prototype,g.prototype,{action_icons_def:g.prototype.action_icons_def.concat([{name:"show_more_rows_icon",title:"To minimize track height, not all feature rows are displayed. Click to display more rows.",css_class:"exclamation",on_click_fn:function(ac){$(".tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw({clear_tile_cache:true})},hide:true}]),copy:function(ac){var ad=this.to_dict();q(ad,{data_manager:this.data_manager});var ae=new this.constructor(this.view,ac,ad);ae.change_mode(this.mode);ae.enabled=this.enabled;return ae},set_filters_manager:function(ac){this.filters_manager=ac;this.header_div.after(this.filters_manager.parent_div)},to_dict:function(){return{track_type:this.get_type(),dataset:{id:this.dataset.id,hda_ldda:this.dataset.get("hda_ldda")},prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},set_min_max:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){var af=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.get("values").mode=ad;if(ad==="Auto"){this.data_manager.clear()}ac.request_draw({clear_tile_cache:true});this.action_icons.mode_icon.attr("title","Set display mode (now: "+ac.mode+")");return ac},update_icons:function(){var ac=this;if(ac.filters_available){ac.action_icons.filters_icon.show()}else{ac.action_icons.filters_icon.hide()}if(ac.tool){ac.action_icons.tools_icon.show();ac.action_icons.param_space_viz_icon.show()}else{ac.action_icons.tools_icon.hide();ac.action_icons.param_space_viz_icon.hide()}},_gen_tile_cache_key:function(ad,ac){return ad+"_"+ac},request_draw:function(ac){if(ac&&ac.clear_tile_cache){this.tile_cache.clear()}this.view.request_redraw(ac,this)},before_draw:function(){this.max_height_px=0},_draw:function(aq){if(!this.can_draw()){return}var an=aq&&aq.clear_after,al=this.view.low,ag=this.view.high,aj=ag-al,ad=this.view.container.width(),ap=this.view.resolution_px_b,af=1/ap;if(this.is_overview){al=this.view.max_low;ag=this.view.max_high;ap=ad/(view.max_high-view.max_low);af=1/ap}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(af*S)),ak,am,ah,ai=[],ao=[];while((ac*S*af)<ag){ak=Math.floor(ac*S*af);am=new y.GenomeRegion({chrom:this.view.chrom,start:ak,end:Math.min(ak+Math.ceil(S*af),this.view.max_high)});ah=this.draw_helper(am,ap,aq);ai.push(ah);$.when(ah).then(function(ar){ao.push(ar)});ac+=1}if(!an){this.tiles_div.children(".remove").removeClass("remove").remove()}var ae=this;$.when.apply($,ai).then(function(){ae.tiles_div.children(".remove").remove();ao=ab.filter(ao,function(ar){return ar!==null});if(ao.length!==0){ae.postdraw_actions(ao,ad,ap,an)}})},_add_yaxis_label:function(af,ah){var ad=this,ag=(af==="max"?"top":"bottom"),ai=(af==="max"?"max":"min"),ac=(af==="max"?"max_value":"min_value"),ae=this.container_div.find(".yaxislabel."+ag);ah=ah||function(){ad.request_draw({clear_tile_cache:true})};if(ae.length!==0){ae.text(ad.prefs[ac])}else{ae=$("<div/>").text(ad.prefs[ac]).make_text_editable({num_cols:12,on_finish:function(aj){$(".tooltip").remove();ad.config.set_param_value(ac,aj);ah()},help_text:"Set "+ai+" value"}).addClass("yaxislabel "+ag).css("color",this.prefs.label_color);this.container_div.prepend(ae)}},postdraw_actions:function(af,ag,ai,ac){var ae=ab.filter(af,function(aj){return(aj instanceof M)});if(ae.length>0){this.max_height_px=0;var ad=this;ab.each(af,function(aj){if(!(aj instanceof M)){aj.html_elt.remove();ad.draw_helper(aj.region,ai,{force:true,mode:"Coverage"})}});ad._add_yaxis_label("max")}else{this.container_div.find(".yaxislabel").remove();var ah=ab.find(af,function(aj){return aj.has_icons});if(ah){ab.each(af,function(aj){if(!aj.has_icons){aj.html_elt.css("padding-top",F)}})}}},get_mode:function(ac){return this.mode},update_auto_mode:function(ac){},_get_drawables:function(){return[this]},draw_helper:function(al,an,ao){if(!ao){ao={}}var ad=ao.force,ai=ao.mode||this.mode,af=1/an,ae=this,ag=this._get_drawables(),am=this._gen_tile_cache_key(an,al),ah=function(ap){return(ap&&"track" in ap)};var aj=(ad?undefined:ae.tile_cache.get_elt(am));if(aj){if(ah(aj)){ae.show_tile(aj,an)}return aj}if(ao.data_fetch===false){return null}var ak=function(){var ap=(ab.find(C,function(ar){return ar===ai})?"Coverage":ai);var aq=ab.map(ag,function(ar){return ar.data_manager.get_data(al,ap,af,ae.data_url_extra_params)});if(view.reference_track){aq.push(view.reference_track.data_manager.get_data(al,ai,af,view.reference_track.data_url_extra_params))}return aq};var ac=$.Deferred();ae.tile_cache.set_elt(am,ac);$.when.apply($,ak()).then(function(){var ap=ak(),av=ap,aB;if(view.reference_track){aB=view.reference_track.data_manager.subset_entry(ap.pop(),al)}var aw=[],at=[];ab.each(ag,function(aG,aD){var aF=aG.mode,aE=av[aD];if(aF==="Auto"){aF=aG.get_mode(aE);aG.update_auto_mode(aF)}aw.push(aF);at.push(aG.get_canvas_height(aE,aF,an,aq))});var au=ae.view.canvas_manager.new_canvas(),ax=al.get("start"),aC=al.get("end"),ar=0,aq=Math.ceil((aC-ax)*an)+ae.left_offset,az=ab.max(at),ay;au.width=aq;au.height=(ao.height||az);var aA=au.getContext("2d");aA.translate(ae.left_offset,0);if(ag.length>1){aA.globalAlpha=0.5;aA.globalCompositeOperation="source-over"}ab.each(ag,function(aE,aD){ay=aE.draw_tile(av[aD],aA,aw[aD],al,an,aB)});if(ay!==undefined){ae.tile_cache.set_elt(am,ay);ae.show_tile(ay,an)}ac.resolve(ay)});return ac},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_line_track_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.LinePainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new M(this,ag,ai,af,ac.data)},draw_tile:function(ac,ad,ag,af,ah,ae){},show_tile:function(ae,ah){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ah;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{this.tiles_div.append(ac)}this.max_height_px=Math.max(this.max_height_px,$(ae.canvas).height());ac.parent().children().css("height",this.max_height_px+"px");var af=this.max_height_px;if(this.visible_height_px!==0){af=Math.min(this.max_height_px,this.visible_height_px)}this.tiles_div.css("height",af+"px")},tool_region_and_parameters_str:function(af){var ac=this,ae=(af!==undefined?af.toString():"all"),ad=ab.values(ac.tool.get_inputs_dict()).join(", ");return" - region=["+ae+"], parameters=["+ad+"]"},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="bigwig"}else{if(ac.dataset_type==="bigwig"||ac.extra_info==="no_detail"){return false}else{return true}}}},can_subset:function(ac){if(ac.message||ac.extra_info==="no_detail"){return false}else{if(ac.dataset_type==="bigwig"){return(ac.data[1][0]-ac.data[0][0]===1)}}return true},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state"}});var W=function(ad,ac){var ae={resize:false};g.call(this,ad,ac,ae);this.container_div.addClass("label-track")};q(W.prototype,g.prototype,{build_header_div:function(){},init:function(){this.enabled=true},predraw_init:function(){},_draw:function(ag){var ae=this.view,af=ae.high-ae.low,aj=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/aj)*aj,ah=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ai=(ac-ae.low)/af*ah;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ai-1}));ac+=aj}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){N.call(this,ad,ac,ag);this.drawables=[];if("drawables" in ag){var af;for(var ae=0;ae<ag.drawables.length;ae++){af=ag.drawables[ae];this.drawables[ae]=p(af,ad,null);if(af.left_offset>this.left_offset){this.left_offset=af.left_offset}}this.enabled=true}ab.each(this.drawables,function(ah){if(ah instanceof d||ah instanceof T){ah.change_mode("Coverage")}});this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,N.prototype,{display_modes:C,action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_group()}}].concat(N.prototype.action_icons_def),to_dict:A.prototype.to_dict,add_drawable:A.prototype.add_drawable,unpack_drawables:A.prototype.unpack_drawables,change_mode:function(ac){N.prototype.change_mode.call(this,ac);for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].change_mode(ac)}},init:function(){var ae=[];for(var ad=0;ad<this.drawables.length;ad++){ae.push(this.drawables[ad].init())}var ac=this;$.when.apply($,ae).then(function(){ac.enabled=true;ac.request_draw()})},update_icons:function(){this.action_icons.filters_icon.hide();this.action_icons.tools_icon.hide();this.action_icons.param_space_viz_icon.hide()},can_draw:r.prototype.can_draw,_get_drawables:function(){return this.drawables},show_group:function(){var af=new P(this.view,this.container,{name:this.prefs.name}),ac;for(var ae=0;ae<this.drawables.length;ae++){ac=this.drawables[ae];ac.update_icons();af.add_drawable(ac);ac.container=af;af.content_div.append(ac.container_div)}var ad=this.container.replace_drawable(this,af,true);af.request_draw({clear_tile_cache:true})},before_draw:function(){N.prototype.before_draw.call(this);var ad=ab.min(ab.map(this.drawables,function(ae){return ae.prefs.min_value})),ac=ab.max(ab.map(this.drawables,function(ae){return ae.prefs.max_value}));this.prefs.min_value=ad;this.prefs.max_value=ac;ab.each(this.drawables,function(ae){ae.prefs.min_value=ad;ae.prefs.max_value=ac})},update_all_min_max:function(){var ac=this;ab.each(this.drawables,function(ad){ad.prefs.min_value=ac.prefs.min_value;ad.prefs.max_value=ac.prefs.max_value});this.request_draw({clear_tile_cache:true})},postdraw_actions:function(ai,ac,al,ah){N.prototype.postdraw_actions.call(this,ai,ac,al,ah);var ag=-1,ae;for(ae=0;ae<ai.length;ae++){var aj=ai[ae].html_elt.find("canvas").height();if(aj>ag){ag=aj}}for(ae=0;ae<ai.length;ae++){var af=ai[ae];if(af.html_elt.find("canvas").height()!==ag){this.draw_helper(af.region,al,{force:true,height:ag});af.html_elt.remove()}}var ad=this,ak=function(){ad.update_all_min_max()};this._add_yaxis_label("min",ak);this._add_yaxis_label("max",ak)}});var D=function(ac){N.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});this.left_offset=ac.canvas_manager.char_width_px;this.container_div.addClass("reference-track");this.data_url=galaxy_config.root+"api/genomes/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new y.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(D.prototype,r.prototype,N.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"height",type:"int",default_value:13,hidden:true}]),build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},predraw_init:function(){},can_draw:r.prototype.can_draw,draw_helper:function(ad,ae,ac){if(ae>this.view.canvas_manager.char_width_px){this.tiles_div.show();return N.prototype.draw_helper.call(this,ad,ae,ac)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(ae,ak,af,ah,al){var ad=this.data_manager.subset_entry(ae,ah),aj=ad.data;var ac=ak.canvas;ak.font=ak.canvas.manager.default_font;ak.textAlign="center";for(var ag=0,ai=aj.length;ag<ai;ag++){ak.fillStyle=this.view.get_base_color(aj[ag]);ak.fillText(aj[ag],Math.floor(ag*al),10)}return new c(this,ah,al,ac,ad)}});var h=function(ad,ac,ae){this.mode="Histogram";N.call(this,ad,ac,ae)};q(h.prototype,r.prototype,N.prototype,{display_modes:C,config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Color",type:"color",default_value:l.get_random_color()},{key:"min_value",label:"Min Value",type:"float",default_value:undefined},{key:"max_value",label:"Max Value",type:"float",default_value:undefined},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:30,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},before_draw:function(){},draw_tile:function(ac,ad,af,ae,ag){return this._draw_line_track_tile(ac,ad,af,ae,ag)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)},postdraw_actions:function(ad,ae,af,ac){this._add_yaxis_label("max");this._add_yaxis_label("min")}});var t=function(ad,ac,ae){this.mode="Heatmap";N.call(this,ad,ac,ae)};q(t.prototype,r.prototype,N.prototype,{display_modes:["Heatmap"],config_params:ab.union(r.prototype.config_params,[{key:"pos_color",label:"Positive Color",type:"color",default_value:"#FF8C00"},{key:"neg_color",label:"Negative Color",type:"color",default_value:"#4169E1"},{key:"min_value",label:"Min Value",type:"float",default_value:-1},{key:"max_value",label:"Max Value",type:"float",default_value:1},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:500,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new c(this,ag,ai,af,ac.data)}});var d=function(ad,ac,ae){N.call(this,ad,ac,ae);this.container_div.addClass("feature-track");this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(d.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true,help:"Show the number of items in each bin when drawing summary histogram"},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"connector_style",label:"Connector style",type:"select",default_value:"fishbones",options:[{label:"Line with arrows",value:"fishbone"},{label:"Arcs",value:"arcs"}]},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.set_painter_from_config();this.request_draw({clear_tile_cache:true})},set_painter_from_config:function(){if(this.config.get("values").connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},postdraw_actions:function(am,ae,an,al){N.prototype.postdraw_actions.call(this,am,ae,an,al);var ag=this,ah;if(ag.filters_manager){var af=ag.filters_manager.filters,aj;for(aj=0;aj<af.length;aj++){af[aj].update_ui_elt()}var ai=false,ak,ad;for(ah=0;ah<am.length;ah++){if(am[ah].data.length){ak=am[ah].data[0];for(aj=0;aj<af.length;aj++){ad=af[aj];if(ad.applies_to(ak)&&ad.min!==ad.max){ai=true;break}}}}if(ag.filters_available!==ai){ag.filters_available=ai;if(!ag.filters_available){ag.filters_manager.hide()}ag.update_icons()}}if(am[0] instanceof O){var ac=true;for(ah=0;ah<am.length;ah++){if(!am[ah].all_slotted){ac=false;break}}if(!ac){this.action_icons.show_more_rows_icon.show()}else{this.action_icons.show_more_rows_icon.hide()}}else{this.action_icons.show_more_rows_icon.hide()}},update_auto_mode:function(ac){if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}this.action_icons.mode_icon.attr("title","Set display mode (now: Auto/"+ac+")")}},incremental_slots:function(ag,ac,af){var ad=this.view.canvas_manager.dummy_context,ae=this.slotters[ag];if(!ae||(ae.mode!==af)){ae=new (u.FeatureSlotter)(ag,af,B,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.extra_info==="no_detail"||this.is_overview){mode="no_detail"}else{if(this.view.high-this.view.low>I){mode="Squish"}else{mode="Pack"}}return mode},get_canvas_height:function(ac,ag,ah,ad){if(ag==="Coverage"||ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var af=this.incremental_slots(ah,ac.data,ag);var ae=new (this.painter)(null,null,null,this.prefs,ag);return Math.max(this.min_height_px,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,af,aj,ae){var ap=this,ad=aq.canvas,ax=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(am.dataset_type==="bigwig"){return this._draw_line_track_tile(am,aq,ao,af,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var ar=0,au=am.data.length;ar<au;ar++){var ah=am.data[ar];var at=false;var al;for(var aw=0,aB=ak.length;aw<aB;aw++){al=ak[aw];al.update_attrs(ah);if(!al.keep(ah)){at=true;break}}if(!at){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aA=(this.filters_manager.alpha_filter?new E(this.filters_manager.alpha_filter):null),ay=(this.filters_manager.height_filter?new E(this.filters_manager.height_filter):null),az=new (this.painter)(ai,ax,ac,this.prefs,ao,aA,ay,ae,function(aC){return ap.view.get_base_color(aC)});var av=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){av=az.draw(aq,ad.width,ad.height,aj,an);av.translation=-ag}return new O(ap,af,aj,ad,am.data,ao,am.message,all_slotted,av)}});var Z=function(ad,ac,ae){N.call(this,ad,ac,ae);this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Histogram color",type:"color",default_value:l.get_random_color()},{key:"show_sample_data",label:"Show sample data",type:"bool",default_value:true},{key:"show_labels",label:"Show summary and sample labels",type:"bool",default_value:true},{key:"summary_height",label:"Locus summary height",type:"float",default_value:20},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,af,ah,ag,ai){if(ac.dataset_type==="bigwig"){return this._draw_line_track_tile(ac,af,"Histogram",ag,ai)}else{var ae=this.view,ad=new (this.painter)(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah,function(aj){return ae.get_base_color(aj)});ad.draw(af,af.canvas.width,af.canvas.height,ai);return new c(this,ag,ai,af.canvas,ac.data)}},get_canvas_height:function(ac,ag,ah,ae){if(ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var ad=(this.dataset.get_metadata("sample_names")?this.dataset.get_metadata("sample_names").length:0);if(ad===0&&ac.data.length!==0){ad=ac.data[0][7].match(/,/g);if(ad===null){ad=1}else{ad=ad.length+1}}var af=new (this.painter)(null,null,null,this.prefs,ag);return af.get_required_height(ad)}},predraw_init:function(){var ac=[g.prototype.predraw_init.call(this)];if(!this.dataset.get_metadata("sample_names")){ac.push(this.dataset.fetch())}return ac},postdraw_actions:function(ag,ah,aj,ad){N.prototype.postdraw_actions.call(this,ag,ah,aj,ad);var af=ab.filter(ag,function(ak){return(ak instanceof M)});var ae=this.dataset.get_metadata("sample_names");if(af.length===0&&this.prefs.show_labels&&ae){var ac;if(this.container_div.find(".yaxislabel.variant").length===0){ac=this.prefs.summary_height/2;this.tiles_div.prepend($("<div/>").text("Summary").addClass("yaxislabel variant top").css({"font-size":ac+"px",top:(this.prefs.summary_height-ac)/2+"px"}));if(this.prefs.show_sample_data){var ai=ae.join("<br/>");this.tiles_div.prepend($("<div/>").html(ai).addClass("yaxislabel variant top sample").css({top:this.prefs.summary_height+2,}))}}ac=(this.mode==="Squish"?5:10)+"px";$(this.tiles_div).find(".sample").css({"font-size":ac,"line-height":ac});$(this.tiles_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel.variant").remove()}}});var T=function(ad,ac,ae){d.call(this,ad,ac,ae);this.painter=(ad.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(T.prototype,r.prototype,N.prototype,d.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block and sense strand color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_insertions",label:"Show insertions",type:"bool",default_value:false},{key:"show_differences",label:"Show differences only",type:"bool",default_value:true},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})}});var e={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:d,LineTrack:h,ReadTrack:T,VariantTrack:Z,VcfTrack:Z};var p=function(ae,ad,ac){if("copy" in ae){return ae.copy(ac)}else{var af=ae.obj_type;if(!af){af=ae.track_type}return new e[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:d,DiagonalHeatmapTrack:t,ReadTrack:T,VariantTrack:Z,CompositeTrack:f,object_from_template:p}});
\ No newline at end of file
+define(["libs/underscore","viz/visualization","viz/trackster/util","viz/trackster/slotting","viz/trackster/painters","viz/trackster/filters","mvc/data","mvc/tools"],function(ab,y,l,u,L,i,X,R){var q=ab.extend;var n={};var k=function(ac,ad){n[ac.attr("id")]=ad};var m=function(ac,ae,ag,af){ag=".group";var ad={};n[ac.attr("id")]=af;ac.bind("drag",{handle:"."+ae,relative:true},function(ao,ap){var an=$(this),at=$(this).parent(),ak=at.children(),am=n[$(this).attr("id")],aj,ai,aq,ah,al;ai=$(this).parents(ag);if(ai.length!==0){aq=ai.position().top;ah=aq+ai.outerHeight();var ar=n[ai.attr("id")];if(ap.offsetY<aq){$(this).insertBefore(ai);ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);ar.remove_drawable(am);ar.container.add_drawable(am);return}}}ai=null;for(al=0;al<ak.length;al++){aj=$(ak.get(al));aq=aj.position().top;ah=aq+aj.outerHeight();if(aj.is(ag)&&this!==aj.get(0)&&ap.offsetY>=aq&&ap.offsetY<=ah){if(ap.offsetY-aq<ah-ap.offsetY){aj.find(".content-div").prepend(this)}else{aj.find(".content-div").append(this)}if(am.container){am.container.remove_drawable(am)}n[aj.attr("id")].add_drawable(am);return}}for(al=0;al<ak.length;al++){aj=$(ak.get(al));if(ap.offsetY<aj.position().top&&!(aj.hasClass("reference-track")||aj.hasClass("intro"))){break}}if(al===ak.length){if(this!==ak.get(al-1)){at.append(this);n[at.attr("id")].move_drawable(am,al)}}else{if(this!==ak.get(al)){$(this).insertBefore(ak.get(al));n[at.attr("id")].move_drawable(am,(ap.deltaY>0?al-1:al))}}}).bind("dragstart",function(){ad["border-top"]=ac.css("border-top");ad["border-bottom"]=ac.css("border-bottom");$(this).css({"border-top":"1px solid blue","border-bottom":"1px solid blue"})}).bind("dragend",function(){$(this).css(ad)})};var F=20,B=100,I=12000,S=400,K=5000,x=100,o="Cannot display dataset due to an error. ",J="A converter for this dataset is not installed. Please check your datatypes_conf.xml file.",G="No data for this chrom/contig.",w="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",z="Tool cannot be rerun: ",b="Loading data...",U="Ready for display",Q=10,H=20,C=["Histogram","Line","Filled","Intensity"];function V(ad,ac){if(!ac){ac=0}var ae=Math.pow(10,ac);return Math.round(ad*ae)/ae}var r=function(ad,ac,af){if(!r.id_counter){r.id_counter=0}this.id=r.id_counter++;this.view=ad;this.container=ac;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.config=new j({params:this.config_params,onchange:this.config_onchange,saved_values:af.prefs});this.prefs=this.config.get("values");if(!this.prefs.name){this.prefs.name=af.name}if(this.config_onchange){this.config.on("change:values",this.config_onchange,this)}this.container_div=this.build_container_div();this.header_div=this.build_header_div();if(this.header_div){this.container_div.append(this.header_div);this.icons_div=$("<div/>").css("float","left").hide().appendTo(this.header_div);this.build_action_icons(this.action_icons_def);this.header_div.append($("<div style='clear: both'/>"));this.header_div.dblclick(function(ag){ag.stopPropagation()});var ae=this;this.container_div.hover(function(){ae.icons_div.show()},function(){ae.icons_div.hide()});$("<div style='clear: both'/>").appendTo(this.container_div)}};r.prototype.action_icons_def=[{name:"toggle_icon",title:"Hide/show content",css_class:"toggle",on_click_fn:function(ac){if(ac.prefs.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.prefs.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.prefs.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var ac=new a({model:ad.config});ac.render()}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".tooltip").remove();ac.remove()}}];q(r.prototype,{config_params:[{key:"name",label:"Name",type:"text",default_value:""},{key:"content_visible",type:"bool",default_value:true,hidden:true}],config_onchange:function(){this.track.set_name(this.track.config.get("values").name)},init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.prefs.content_visible){return true}return false},request_draw:function(){},_draw:function(ac){},to_dict:function(){},set_name:function(ac){this.old_name=this.prefs.name;this.prefs.name=ac;this.name_div.text(this.prefs.name)},revert_name:function(){if(this.old_name){this.prefs.name=this.old_name;this.name_div.text(this.prefs.name)}},remove:function(){this.changed();this.container.remove_drawable(this);var ac=this.view;this.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})},build_container_div:function(){},build_header_div:function(){},add_action_icon:function(ad,ai,ah,ag,ac,af){var ae=this;this.action_icons[ad]=$("<a/>").attr("title",ai).addClass("icon-button").addClass(ah).tooltip().click(function(){ag(ae)}).appendTo(this.icons_div);if(af){this.action_icons[ad].hide()}},build_action_icons:function(ac){var ae;for(var ad=0;ad<ac.length;ad++){ae=ac[ad];this.add_action_icon(ae.name,ae.title,ae.css_class,ae.on_click_fn,ae.prepend,ae.hide)}},update_icons:function(){},hide_contents:function(){},show_contents:function(){},get_drawables:function(){}});var A=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(A.prototype,r.prototype,{unpack_drawables:function(ae){this.drawables=[];var ad;for(var ac=0;ac<ae.length;ac++){ad=p(ae[ac],this.view,this);this.add_drawable(ad)}},init:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].init()}},_draw:function(ac){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad]._draw(ac)}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{prefs:this.prefs,obj_type:this.obj_type,drawables:ad}},add_drawable:function(ac){this.drawables.push(ac);ac.container=this;this.changed()},add_drawable_before:function(ae,ac){this.changed();var ad=this.drawables.indexOf(ac);if(ad!==-1){this.drawables.splice(ad,0,ae);return true}return false},replace_drawable:function(ae,ac,ad){var af=this.drawables.indexOf(ae);if(af!==-1){this.drawables[af]=ac;if(ad){ae.container_div.replaceWith(ac.container_div)}this.changed()}return af},remove_drawable:function(ad){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);ad.container=null;this.changed();return true}return false},move_drawable:function(ad,ae){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);this.drawables.splice(ae,0,ad);this.changed();return true}return false},get_drawables:function(){return this.drawables},get_tracks:function(af){var ac=this.drawables.slice(0),ad=[],ae;while(ac.length!==0){ae=ac.shift();if(ae instanceof af){ad.push(ae)}else{if(ae.drawables){ac=ac.concat(ae.drawables)}}}return ad}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});A.call(this,ad,ac,af);this.content_div=$("<div/>").addClass("content-div").attr("id","group_"+this.id+"_content_div").appendTo(this.container_div);k(this.container_div,this);k(this.content_div,this);m(this.container_div,this.drag_handle_class,".group",this);this.filters_manager=new i.FiltersManager(this);this.header_div.after(this.filters_manager.parent_div);this.saved_filters_managers=[];if("drawables" in af){this.unpack_drawables(af.drawables)}if("filters" in af){var ae=this.filters_manager;this.filters_manager=new i.FiltersManager(this,af.filters);ae.parent_div.replaceWith(this.filters_manager.parent_div);if(af.filters.visible){this.setup_multitrack_filtering()}}};q(P.prototype,r.prototype,A.prototype,{action_icons_def:[r.prototype.action_icons_def[0],r.prototype.action_icons_def[1],{name:"composite_icon",title:"Show composite track",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_composite_track()}},{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters();ac._restore_filter_managers()}else{ac.setup_multitrack_filtering();ac.request_draw({clear_tile_cache:true})}ac.filters_manager.toggle()}},r.prototype.action_icons_def[2]],build_container_div:function(){var ac=$("<div/>").addClass("group").attr("id","group_"+this.id);if(this.container){this.container.content_div.append(ac)}return ac},build_header_div:function(){var ac=$("<div/>").addClass("track-header");ac.append($("<div/>").addClass(this.drag_handle_class));this.name_div=$("<div/>").addClass("track-name").text(this.prefs.name).appendTo(ac);return ac},hide_contents:function(){this.tiles_div.hide()},show_contents:function(){this.tiles_div.show();this.request_draw()},update_icons:function(){var ae=this.drawables.length;if(ae===0){this.action_icons.composite_icon.hide();this.action_icons.filters_icon.hide()}else{if(ae===1){if(this.drawables[0] instanceof f){this.action_icons.composite_icon.show()}this.action_icons.filters_icon.hide()}else{var al,ak,ai,ao=true,ag=this.drawables[0].get_type(),ac=0;for(al=0;al<ae;al++){ai=this.drawables[al];if(ai.get_type()!==ag){can_composite=false;break}if(ai instanceof d){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".tooltip").remove()}if(ac>1&&ac===this.drawables.length){var ap={},ad;ai=this.drawables[0];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];ap[ad.name]=[ad]}for(al=1;al<this.drawables.length;al++){ai=this.drawables[al];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];if(ad.name in ap){ap[ad.name].push(ad)}}}this.filters_manager.remove_all();var af,ah,aj,am;for(var an in ap){af=ap[an];if(af.length===ac){ah=new i.NumberFilter({name:af[0].name,index:af[0].index});this.filters_manager.add_filter(ah)}}if(this.filters_manager.filters.length>0){this.action_icons.filters_icon.show()}else{this.action_icons.filters_icon.hide()}}else{this.action_icons.filters_icon.hide()}}}},_restore_filter_managers:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].filters_manager=this.saved_filters_managers[ac]}this.saved_filters_managers=[]},setup_multitrack_filtering:function(){if(this.filters_manager.filters.length>0){this.saved_filters_managers=[];for(var ac=0;ac<this.drawables.length;ac++){drawable=this.drawables[ac];this.saved_filters_managers.push(drawable.filters_manager);drawable.filters_manager=this.filters_manager}}this.filters_manager.init_filters()},show_composite_track:function(){var ad=new f(this.view,this.view,{name:this.prefs.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ad,true);ad.request_draw()},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){A.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(A.prototype.to_dict.call(this),{filters:this.filters_manager.to_dict()});if(this.filters_manager.visible()){this.setup_multitrack_filtering()}return ac},request_draw:function(ac){ab.each(this.drawables,function(ad){ad.request_draw(ac)})}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});A.call(this,"View",ac.container,ac);this.chrom=null;this.vis_id=ac.vis_id;this.dbkey=ac.dbkey;this.label_tracks=[];this.tracks_to_be_redrawn=[];this.max_low=0;this.max_high=0;this.zoom_factor=3;this.min_separation=30;this.has_changes=false;this.load_chroms_deferred=null;this.render();this.canvas_manager=new y.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new j({track:this,params:[{key:"a_color",label:"A Color",type:"color",default_value:"#FF0000"},{key:"c_color",label:"C Color",type:"color",default_value:"#00FF00"},{key:"g_color",label:"G Color",type:"color",default_value:"#0000FF"},{key:"t_color",label:"T Color",type:"color",default_value:"#FF00FF"},{key:"n_color",label:"N Color",type:"color",default_value:"#AAAAAA"}],saved_values:ac.prefs,onchange:function(){track.request_redraw({clear_tile_cache:true})}})},render:function(){this.requested_redraw=false;var ae=this.container,ac=this;this.top_container=$("<div/>").addClass("top-container").appendTo(ae);this.browser_content_div=$("<div/>").addClass("content").css("position","relative").appendTo(ae);this.bottom_container=$("<div/>").addClass("bottom-container").appendTo(ae);this.top_labeltrack=$("<div/>").addClass("top-labeltrack").appendTo(this.top_container);this.viewport_container=$("<div/>").addClass("viewport-container").attr("id","viewport-container").appendTo(this.browser_content_div);this.content_div=this.viewport_container;k(this.viewport_container,ac);this.intro_div=$("<div/>").addClass("intro").appendTo(this.viewport_container).hide();var af=$("<div/>").text("Add Datasets to Visualization").addClass("action-button").appendTo(this.intro_div).click(function(){y.select_datasets(galaxy_config.root+"visualization/list_current_history_datasets",galaxy_config.root+"api/datasets",{"f-dbkey":ac.dbkey},function(ag){ab.each(ag,function(ah){ac.add_drawable(p(ah,ac,ac))})})});this.nav_labeltrack=$("<div/>").addClass("nav-labeltrack").appendTo(this.bottom_container);this.nav_container=$("<div/>").addClass("trackster-nav-container").prependTo(this.top_container);this.nav=$("<div/>").addClass("trackster-nav").appendTo(this.nav_container);this.overview=$("<div/>").addClass("overview").appendTo(this.bottom_container);this.overview_viewport=$("<div/>").addClass("overview-viewport").appendTo(this.overview);this.overview_close=$("<a/>").attr("title","Close overview").addClass("icon-button overview-close tooltip").hide().appendTo(this.overview_viewport);this.overview_highlight=$("<div/>").addClass("overview-highlight").hide().appendTo(this.overview_viewport);this.overview_box_background=$("<div/>").addClass("overview-boxback").appendTo(this.overview_viewport);this.overview_box=$("<div/>").addClass("overview-box").appendTo(this.overview_viewport);this.default_overview_height=this.overview_box.height();this.nav_controls=$("<div/>").addClass("nav-controls").appendTo(this.nav);this.chrom_select=$("<select/>").attr({name:"chrom"}).css("width","15em").append("<option value=''>Loading</option>").appendTo(this.nav_controls);var ad=function(ag){if(ag.type==="focusout"||(ag.keyCode||ag.which)===13||(ag.keyCode||ag.which)===27){if((ag.keyCode||ag.which)!==27){ac.go_to($(this).val())}$(this).hide();$(this).val("");ac.location_span.show();ac.chrom_select.show()}};this.nav_input=$("<input/>").addClass("nav-input").hide().bind("keyup focusout",ad).appendTo(this.nav_controls);this.location_span=$("<span/>").addClass("location").attr("original-title","Click to change location").tooltip({placement:"bottom"}).appendTo(this.nav_controls);this.location_span.click(function(){ac.location_span.hide();ac.chrom_select.hide();ac.nav_input.val(ac.chrom+":"+ac.low+"-"+ac.high);ac.nav_input.css("display","inline-block");ac.nav_input.select();ac.nav_input.focus();ac.nav_input.autocomplete({source:function(ai,ag){var aj=[],ah=$.map(ac.get_tracks(d),function(ak){return ak.data_manager.search_features(ai.term).success(function(al){aj=aj.concat(al)})});$.when.apply($,ah).done(function(){ag($.map(aj,function(ak){return{label:ak[0],value:ak[1]}}))})}})});if(this.vis_id!==undefined){this.hidden_input=$("<input/>").attr("type","hidden").val(this.vis_id).appendTo(this.nav_controls)}this.zo_link=$("<a/>").attr("id","zoom-out").attr("title","Zoom out").tooltip({placement:"bottom"}).click(function(){ac.zoom_out();ac.request_redraw()}).appendTo(this.nav_controls);this.zi_link=$("<a/>").attr("id","zoom-in").attr("title","Zoom in").tooltip({placement:"bottom"}).click(function(){ac.zoom_in();ac.request_redraw()}).appendTo(this.nav_controls);this.load_chroms_deferred=this.load_chroms({low:0});this.chrom_select.bind("change",function(){ac.change_chrom(ac.chrom_select.val())});this.browser_content_div.click(function(ag){$(this).find("input").trigger("blur")});this.browser_content_div.bind("dblclick",function(ag){ac.zoom_in(ag.pageX,this.viewport_container)});this.overview_box.bind("dragstart",function(ag,ah){this.current_x=ah.offsetX}).bind("drag",function(ag,ai){var aj=ai.offsetX-this.current_x;this.current_x=ai.offsetX;var ah=Math.round(aj/ac.viewport_container.width()*(ac.max_high-ac.max_low));ac.move_delta(-ah)});this.overview_close.click(function(){ac.reset_overview()});this.viewport_container.bind("draginit",function(ag,ah){if(ag.clientX>ac.viewport_container.width()-16){return false}}).bind("dragstart",function(ag,ah){ah.original_low=ac.low;ah.current_height=ag.clientY;ah.current_x=ah.offsetX}).bind("drag",function(ai,ak){var ag=$(this);var al=ak.offsetX-ak.current_x;var ah=ag.scrollTop()-(ai.clientY-ak.current_height);ag.scrollTop(ah);ak.current_height=ai.clientY;ak.current_x=ak.offsetX;var aj=Math.round(al/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}).bind("mousewheel",function(ai,ak,ah,ag){if(ah){ah*=50;var aj=Math.round(-ah/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}});this.top_labeltrack.bind("dragstart",function(ag,ah){return $("<div />").css({height:ac.browser_content_div.height()+ac.top_labeltrack.height()+ac.nav_labeltrack.height()+1,top:"0px",position:"absolute","background-color":"#ccf",opacity:0.5,"z-index":1000}).appendTo($(this))}).bind("drag",function(ak,al){$(al.proxy).css({left:Math.min(ak.pageX,al.startX)-ac.container.offset().left,width:Math.abs(ak.pageX-al.startX)});var ah=Math.min(ak.pageX,al.startX)-ac.container.offset().left,ag=Math.max(ak.pageX,al.startX)-ac.container.offset().left,aj=(ac.high-ac.low),ai=ac.viewport_container.width();ac.update_location(Math.round(ah/ai*aj)+ac.low,Math.round(ag/ai*aj)+ac.low)}).bind("dragend",function(al,am){var ah=Math.min(al.pageX,am.startX),ag=Math.max(al.pageX,am.startX),aj=(ac.high-ac.low),ai=ac.viewport_container.width(),ak=ac.low;ac.low=Math.round(ah/ai*aj)+ak;ac.high=Math.round(ag/ai*aj)+ak;$(am.proxy).remove();ac.request_redraw()});this.add_label_track(new W(this,{content_div:this.top_labeltrack}));this.add_label_track(new W(this,{content_div:this.nav_labeltrack}));$(window).bind("resize",function(){if(this.resize_timer){clearTimeout(this.resize_timer)}this.resize_timer=setTimeout(function(){ac.resize_window()},500)});$(document).bind("redraw",function(){ac.redraw()});this.reset();$(window).trigger("resize")},get_base_color:function(ac){return this.config.get("values")[ac.toLowerCase()+"_color"]||this.config.get("values").n_color}});q(Y.prototype,A.prototype,{changed:function(){this.has_changes=true},update_intro_div:function(){if(this.drawables.length===0){this.intro_div.show()}else{this.intro_div.hide()}},trigger_navigate:function(ad,af,ac,ag){if(this.timer){clearTimeout(this.timer)}if(ag){var ae=this;this.timer=setTimeout(function(){ae.trigger("navigate",ad+":"+af+"-"+ac)},500)}else{view.trigger("navigate",ad+":"+af+"-"+ac)}},update_location:function(ac,ae){this.location_span.text(commatize(ac)+" - "+commatize(ae));this.nav_input.val(this.chrom+":"+commatize(ac)+"-"+commatize(ae));var ad=view.chrom_select.val();if(ad!==""){this.trigger_navigate(ad,view.low,view.high,true)}},load_chroms:function(ae){ae.num=x;var ac=this,ad=$.Deferred();$.ajax({url:galaxy_config.root+"api/genomes/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){var ah=new D(ac);ac.add_label_track(ah);ac.reference_track=ah}ac.chrom_data=ag.chrom_info;var ak='<option value="">Select Chrom/Contig</option>';for(var aj=0,af=ac.chrom_data.length;aj<af;aj++){var ai=ac.chrom_data[aj].chrom;ak+='<option value="'+ai+'">'+ai+"</option>"}if(ag.prev_chroms){ak+='<option value="previous">Previous '+x+"</option>"}if(ag.next_chroms){ak+='<option value="next">Next '+x+"</option>"}ac.chrom_select.html(ak);ac.chrom_start_index=ag.start_index;ad.resolve(ag.chrom_info)},error:function(){alert("Could not load chroms for this dbkey:",ac.dbkey)}});return ad},change_chrom:function(ah,ad,aj){var ae=this;if(!ae.chrom_data){ae.load_chroms_deferred.then(function(){ae.change_chrom(ah,ad,aj)});return}if(!ah||ah==="None"){return}if(ah==="previous"){ae.load_chroms({low:this.chrom_start_index-x});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+x});return}var ai=$.grep(ae.chrom_data,function(ak,al){return ak.chrom===ah})[0];if(ai===undefined){ae.load_chroms({chrom:ah},function(){ae.change_chrom(ah,ad,aj)});return}else{if(ah!==ae.chrom){ae.chrom=ah;ae.chrom_select.val(ae.chrom);ae.max_high=ai.len-1;ae.reset();for(var ag=0,ac=ae.drawables.length;ag<ac;ag++){var af=ae.drawables[ag];if(af.init){af.init()}}if(ae.reference_track){ae.reference_track.init()}}if(ad&&aj){ae.low=Math.max(ad,0);ae.high=Math.min(aj,ae.max_high)}else{ae.low=0;ae.high=ae.max_high}ae.reset_overview();ae.request_redraw()}},go_to:function(ag){ag=ag.replace(/,/g,"");ag=ag.replace(/:|\-/g," ");var ad=ag.split(/\s+/),af=ad[0],ae=(ad[1]?parseInt(ad[1],10):null),ac=(ad[2]?parseInt(ad[2],10):null);if(!ac){ae=ae-15;ac=ae+15}this.change_chrom(af,ae,ac)},move_fraction:function(ae){var ac=this;var ad=ac.high-ac.low;this.move_delta(ae*ad)},move_delta:function(af){var ac=this;var ae=ac.high-ac.low;if(ac.low-af<ac.max_low){ac.low=ac.max_low;ac.high=ac.max_low+ae}else{if(ac.high-af>ac.max_high){ac.high=ac.max_high;ac.low=ac.max_high-ae}else{ac.high-=af;ac.low-=af}}ac.request_redraw({data_fetch:false});if(this.redraw_on_move_fn){clearTimeout(this.redraw_on_move_fn)}this.redraw_on_move_fn=setTimeout(function(){ac.request_redraw()},200);var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);ac.init();this.changed();this.update_intro_div()},add_label_track:function(ac){ac.view=this;ac.init();this.label_tracks.push(ac)},remove_drawable:function(ae,ad){A.prototype.remove_drawable.call(this,ae);if(ad){var ac=this;ae.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})}},reset:function(){this.low=this.max_low;this.high=this.max_high;this.viewport_container.find(".yaxislabel").remove()},request_redraw:function(ad,ae){var ac=this,af=(ae?[ae]:ac.drawables);ab.each(af,function(ag){var ah=ab.find(ac.tracks_to_be_redrawn,function(ai){return ai[0]===ag});if(ah){ah[1]=ad}else{ac.tracks_to_be_redrawn.push([ag,ad])}});if(!this.requested_redraw){requestAnimationFrame(function(){ac._redraw()});this.requested_redraw=true}},_redraw:function(){this.requested_redraw=false;var ac=this.low,ag=this.high;if(ac<this.max_low){ac=this.max_low}if(ag>this.max_high){ag=this.max_high}var ad=this.high-this.low;if(this.high!==0&&ad<this.min_separation){ag=ac+this.min_separation}this.low=Math.floor(ac);this.high=Math.ceil(ag);this.update_location(this.low,this.high);this.resolution_px_b=this.viewport_container.width()/(this.high-this.low);var af=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ah=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ae=13;this.overview_box.css({left:af,width:Math.max(ae,ah)}).show();if(ah<ae){this.overview_box.css("left",af-(ae-ah)/2)}if(this.overview_highlight){this.overview_highlight.css({left:af,width:ah})}ab.each(this.tracks_to_be_redrawn,function(ak){var ai=ak[0],aj=ak[1];if(ai){ai._draw(aj)}});this.tracks_to_be_redrawn=[];ab.each(this.label_tracks,function(ai){ai._draw()})},zoom_in:function(ad,ae){if(this.max_high===0||this.high-this.low<=this.min_separation){return}var af=this.high-this.low,ag=af/2+this.low,ac=(af/this.zoom_factor)/2;if(ad){ag=ad/this.viewport_container.width()*(this.high-this.low)+this.low}this.low=Math.round(ag-ac);this.high=Math.round(ag+ac);this.changed();this.request_redraw()},zoom_out:function(){if(this.max_high===0){return}var ad=this.high-this.low,ae=ad/2+this.low,ac=(ad*this.zoom_factor)/2;this.low=Math.round(ae-ac);this.high=Math.round(ae+ac);this.changed();this.request_redraw()},resize_window:function(){this.viewport_container.height(this.container.height()-this.top_container.height()-this.bottom_container.height());this.request_redraw()},set_overview:function(ae){if(this.overview_drawable){if(this.overview_drawable.dataset.id===ae.dataset.id){return}this.overview_viewport.find(".track").remove()}var ad=ae.copy({content_div:this.overview_viewport}),ac=this;ad.header_div.hide();ad.is_overview=true;ac.overview_drawable=ad;this.overview_drawable.postdraw_actions=function(){ac.overview_highlight.show().height(ac.overview_drawable.content_div.height());ac.overview_viewport.height(ac.overview_drawable.content_div.height()+ac.overview_box.outerHeight());ac.overview_close.show();ac.resize_window()};ac.overview_drawable.request_draw();this.changed()},reset_overview:function(){$(".tooltip").remove();this.overview_viewport.find(".track-tile").remove();this.overview_viewport.height(this.default_overview_height);this.overview_box.height(this.default_overview_height);this.overview_close.hide();this.overview_highlight.hide();view.resize_window();view.overview_drawable=null}});var s=R.Tool.extend({defaults:{track:null},initialize:function(ac){if(ac.tool_state!==undefined){this.set("hidden",ac.tool_state.hidden)}this.remove_inputs(["data","hidden_data","conditional"])},state_dict:function(ac){return ab.extend(this.get_inputs_dict(),{hidden:!this.is_visible()})}});var v=Backbone.View.extend({events:{"change input":"update_value"},render:function(){var ae=this.$el.addClass("param-row"),af=this.model;var ac=$("<div>").addClass("param-label").text(af.get("label")).appendTo(ae);var ad=$("<div/>").addClass("param-input").html(af.get("html")).appendTo(ae);ad.find(":input").val(af.get("value"));$("<div style='clear: both;'/>").appendTo(ae)},update_value:function(ac){this.model.set_value($(ac.target).val())}});var aa=Backbone.View.extend({initialize:function(ac){this.model.on("change:hidden",this.set_visible,this)},render:function(){var ad=this;tool=this.model,parent_div=this.$el.addClass("dynamic-tool").hide();parent_div.bind("drag",function(ah){ah.stopPropagation()}).click(function(ah){ah.stopPropagation()}).bind("dblclick",function(ah){ah.stopPropagation()}).keydown(function(ah){ah.stopPropagation()});var ae=$("<div class='tool-name'>").appendTo(parent_div).text(tool.get("name"));tool.get("inputs").each(function(ai){var ah=new v({model:ai});ah.render();parent_div.append(ah.$el)});parent_div.find("input").click(function(){$(this).select()});var af=$("<div>").addClass("param-row").appendTo(parent_div);var ag=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(af);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(af);ac.click(function(){ad.run_on_region()});ag.click(function(){ad.run_on_dataset()});if(tool.is_visible()){this.$el.show()}},set_visible:function(){if(this.model.is_visible()){this.$el.show()}else{this.$el.hide()}},update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},run_on_dataset:function(){var ac=this.model;this.run({target_dataset_id:this.model.get("track").dataset.id,action:"rerun",tool_id:ac.id},null,function(ad){Galaxy.modal.show({title:ac.get("name")+" is Running",body:ac.get("name")+" is running on the complete dataset. Tool outputs are in dataset's history.",buttons:{Close:function(){Galaxy.modal.hide()}}})})},run_on_region:function(){var ad=this.model.get("track"),ag=this.model,ai=new y.GenomeRegion({chrom:ad.view.chrom,start:ad.view.low,end:ad.view.high}),aj={target_dataset_id:ad.dataset.id,action:"rerun",tool_id:ag.id,regions:[ai.toJSON()]},ah=ad,al=aj.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ak=new P(view,view,{name:this.prefs.name});var af=ah.container.replace_drawable(ah,ak,false);ak.container_div.insertBefore(ah.view.content_div.children()[af]);ak.add_drawable(ah);ah.container_div.appendTo(ak.content_div);ac=ak}else{ac=ah.container}var ae=new ah.constructor(view,ac,{name:al,hda_ldda:"hda"});ae.init_for_tool_data();ae.change_mode(ah.mode);ae.set_filters_manager(ah.filters_manager.copy(ae));ae.update_icons();ac.add_drawable(ae);ae.tiles_div.text("Starting job.");this.run(aj,ae,function(am){ae.set_dataset(new X.Dataset(am));ae.tiles_div.text("Running job.");ae.init()})},run:function(ac,ae,af){ac.inputs=this.model.get_inputs_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_config.root+"api/tools",data:JSON.stringify(ac),dataType:"json",contentType:"application/json",type:"POST"},interval:2000,success_fn:function(ag){return ag!=="pending"}});$.when(ad.go()).then(function(ag){if(ag==="no converter"){ae.container_div.addClass("error");ae.content_div.text(J)}else{if(ag.error){ae.container_div.addClass("error");ae.content_div.text(z+ag.message)}else{af(ag)}}})}});var E=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};E.prototype.gen_val=function(ac){if(this.filter.high===Number.MAX_VALUE||this.filter.low===-Number.MAX_VALUE||this.filter.low===this.filter.high){return this.default_val}return((parseFloat(ac[this.filter.index])-this.filter.low)/(this.filter.high-this.filter.low))};var j=Backbone.Model.extend({initialize:function(ad){var ac={};ab.each(ad.params,function(ae){ac[ae.key]=ae.default_value});if(ad.saved_values){ab.each(this.get("params"),function(ae){if(ae.key in ad.saved_values){ac[ae.key]=ad.saved_values[ae.key]}})}this.set("values",ac)},set_param_default_value:function(ad,ac){var ae=ab.find(this.get("params"),function(af){return af.key===ad});if(ae){ae.default_value=ac}},set_param_value:function(ac,ad){var ae=ab.find(this.get("params"),function(af){return af.key===ac});if(ae){if(typeof ad==="string"||ad instanceof String){if(ad.trim()===""){ad=ae.default_value}else{if(ae.type==="float"){ad=parseFloat(ad)}else{if(ae.type==="int"){ad=parseInt(ad,10)}}}}}if(this.get("values")[ac]!==ad){this.get("values")[ac]=ad;this.trigger("change:values");return true}else{return false}}});var a=Backbone.View.extend({render:function(){var aj=this.model;var ac=$("<div/>").keydown(function(ak){ak.stopPropagation()});var ai;function ah(ao,ak){for(var at=0;at<ao.length;at++){ai=ao[at];if(ai.hidden){continue}var am="param_"+at;var ax=aj.get("values")[ai.key];var az=$("<div class='form-row' />").appendTo(ak);az.append($("<label />").attr("for",am).text(ai.label+":"));if(ai.type==="bool"){az.append($('<input type="checkbox" />').attr("id",am).attr("name",am).attr("checked",ax))}else{if(ai.type==="text"){az.append($('<input type="text"/>').attr("id",am).val(ax).click(function(){$(this).select()}))}else{if(ai.type==="select"){var av=$("<select />").attr("id",am);for(var aq=0;aq<ai.options.length;aq++){$("<option/>").text(ai.options[aq].label).attr("value",ai.options[aq].value).appendTo(av)}av.val(ax);az.append(av)}else{if(ai.type==="color"){var ay=$("<div/>").appendTo(az),au=$("<input />").attr("id",am).attr("name",am).val(ax).css("float","left").appendTo(ay).click(function(aB){$(".tooltip").removeClass("in");var aA=$(this).siblings(".tooltip").addClass("in");aA.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top+Galaxy.modal.scrollTop()-($(aA).height()/2)+($(this).height()/2)}).show();aA.click(function(aC){aC.stopPropagation()});$(document).bind("click.color-picker",function(){aA.hide();$(document).unbind("click.color-picker")});aB.stopPropagation()}),ar=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(ay).attr("title","Set new random color").tooltip(),aw=$("<div class='tooltip right' style='position: absolute;' />").appendTo(ay).hide(),an=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(aw),al=$("<div class='tooltip-arrow'></div>").appendTo(aw),ap=$.farbtastic(an,{width:100,height:100,callback:au,color:ax});ay.append($("<div/>").css("clear","both"));(function(aA){ar.click(function(){aA.setColor(l.get_random_color())})})(ap)}else{az.append($("<input />").attr("id",am).attr("name",am).val(ax))}}}}if(ai.help){az.append($("<div class='help'/>").text(ai.help))}}}ah(aj.get("params"),ac);var ad=this,ag=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ae=function(){ad.update_from_form($(Galaxy.modal.el));Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},af=function(ak){if((ak.keyCode||ak.which)===27){ag()}else{if((ak.keyCode||ak.which)===13){ae()}}};$(window).bind("keypress.check_enter_esc",af);Galaxy.modal.show({title:"Configure",body:ac,buttons:{Cancel:ag,Ok:ae}})},update_from_form:function(ac){var ad=this.model;var ae=false;ab.each(ad.get("params"),function(ah,af){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}ae=ad.set_param_value(ah.key,ag)||ae}})}});var c=function(ac,af,ag,ad,ae){this.track=ac;this.region=af;this.low=af.get("start");this.high=af.get("end");this.w_scale=ag;this.canvas=ad;this.html_elt=$("<div class='track-tile'/>").append(ad);this.data=ae;this.stale=false};c.prototype.predisplay_actions=function(){};var M=function(ac,af,ag,ad,ae){c.call(this,ac,af,ag,ad,ae)};M.prototype.predisplay_actions=function(){};var O=function(af,am,ao,ae,ah,ai,ap,ad,al){c.call(this,af,am,ao,ae,ah);this.mode=ai;this.all_slotted=ad;this.feature_mapper=al;this.has_icons=false;if(ap){this.has_icons=true;var aj=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:F,width:ae.width}).prependTo(this.html_elt);var ak=new y.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),an=ah.length,ag=$("<a/>").addClass("icon more-down").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a/>").addClass("icon more-across").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ag.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.DEEP_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()});ac.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.BROAD_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()})}};q(O.prototype,c.prototype);O.prototype.predisplay_actions=function(){var ad=this,ac={};if(ad.mode!=="Pack"){return}$(this.html_elt).hover(function(){this.hovered=true;$(this).mousemove()},function(){this.hovered=false;$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()}).mousemove(function(ao){if(!this.hovered){return}var aj=$(this).offset(),an=ao.pageX-aj.left,am=ao.pageY-aj.top,at=ad.feature_mapper.get_feature_data(an,am),ak=(at?at[0]:null);$(this).parents(".track-content").children(".overlay").children(".feature-popup").each(function(){if(!ak||$(this).attr("id")!==ak.toString()){$(this).remove()}});if(at){var af=ac[ak];if(!af){var ap={name:at[3],start:at[1],end:at[2],strand:at[4]},ai=ad.track.filters_manager.filters,ah;for(var al=0;al<ai.length;al++){ah=ai[al];ap[ah.name]=at[ah.index]}af=$("<div/>").attr("id",ak).addClass("feature-popup");var au=$("<table/>"),ar,aq,av;for(ar in ap){aq=ap[ar];av=$("<tr/>").appendTo(au);$("<th/>").appendTo(av).text(ar);$("<td/>").attr("align","left").appendTo(av).text(typeof(aq)==="number"?V(aq,2):aq)}af.append($("<div class='feature-popup-inner'>").append(au));ac[ak]=af}af.appendTo($(this).parents(".track-content").children(".overlay"));var ag=an+parseInt(ad.html_elt.css("left"),10)-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"),10)+7;af.css("left",ag+"px").css("top",ae+"px")}else{if(!ao.isPropagationStopped()){ao.stopPropagation();$(this).siblings().each(function(){$(this).trigger(ao)})}}}).mouseleave(function(){$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()})};var g=function(ad,ac,ae){q(ae,{drag_handle_class:"draghandle"});r.call(this,ad,ac,ae);this.dataset=null;if(ae.dataset){this.dataset=(ae.dataset instanceof Backbone.Model?ae.dataset:X.Dataset.findOrCreate(ae.dataset))}this.dataset_check_type="converted_datasets_state";this.data_url_extra_params={};this.data_query_wait=("data_query_wait" in ae?ae.data_query_wait:K);this.data_manager=("data_manager" in ae?ae.data_manager:new y.GenomeDataManager({dataset:this.dataset,genome:new y.Genome({key:ad.dbkey,chroms_info:{chrom_info:ad.chrom_data}}),data_mode_compatible:this.data_and_mode_compatible,can_subset:this.can_subset}));this.min_height_px=16;this.max_height_px=800;this.visible_height_px=this.prefs.height;this.content_div=$("<div class='track-content'>").appendTo(this.container_div);if(this.container){this.container.content_div.append(this.container_div);if(!("resize" in ae)||ae.resize){this.add_resize_handle()}}};q(g.prototype,r.prototype,{action_icons_def:[{name:"mode_icon",title:"Set display mode",css_class:"chevron-expand",on_click_fn:function(){}},r.prototype.action_icons_def[0],{name:"overview_icon",title:"Set as overview",css_class:"overview-icon",on_click_fn:function(ac){ac.view.set_overview(ac)}},r.prototype.action_icons_def[1],{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters()}else{ac.filters_manager.init_filters()}ac.filters_manager.toggle()}},{name:"tools_icon",title:"Tool",css_class:"hammer",on_click_fn:function(ac){ac.tool.toggle();if(ac.tool.is_visible()){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".tooltip").remove()}},{name:"param_space_viz_icon",title:"Tool parameter space visualization",css_class:"arrow-split",on_click_fn:function(ac){var af='<strong>Tool</strong>: <%= track.tool.name %><br/><strong>Dataset</strong>: <%= track.name %><br/><strong>Region(s)</strong>: <select name="regions"><option value="cur">current viewing area</option><option value="bookmarks">bookmarks</option><option value="both">current viewing area and bookmarks</option></select>',ae=ab.template(af,{track:ac});var ah=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new y.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new y.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}Galaxy.modal.hide();window.location.href=galaxy_config.root+"visualization/sweepster?"+$.param({dataset_id:ac.dataset.id,hda_ldda:ac.dataset.get("hda_ldda"),regions:JSON.stringify(new Backbone.Collection(al).toJSON())})},ag=function(ai){if((ai.keyCode||ai.which)===27){ah()}else{if((ai.keyCode||ai.which)===13){ad()}}};Galaxy.modal.show({title:"Visualize tool parameter space and output from different parameter settings?",body:ae,buttons:{No:ah,Yes:ad}})}},r.prototype.action_icons_def[2]],can_draw:function(){return this.dataset&&r.prototype.can_draw.call(this)},build_container_div:function(){return $("<div/>").addClass("track").attr("id","track_"+this.id).css("position","relative")},build_header_div:function(){var ac=$("<div class='track-header'/>");if(this.view.editor){this.drag_div=$("<div/>").addClass(this.drag_handle_class).appendTo(ac)}this.name_div=$("<div/>").addClass("track-name").appendTo(ac).text(this.prefs.name).attr("id",this.prefs.name.replace(/\s+/g,"-").replace(/[^a-zA-Z0-9\-]/g,"").toLowerCase());return ac},set_dataset:function(ac){this.dataset=ac;this.data_manager.set("dataset",ac)},on_resize:function(){this.request_draw({clear_tile_cache:true})},add_resize_handle:function(){var ac=this;var af=false;var ae=false;var ad=$("<div class='track-resize'>");$(ac.container_div).hover(function(){if(ac.prefs.content_visible){af=true;ad.show()}},function(){af=false;if(!ae){ad.hide()}});ad.hide().bind("dragstart",function(ag,ah){ae=true;ah.original_height=$(ac.content_div).height()}).bind("drag",function(ah,ai){var ag=Math.min(Math.max(ai.original_height+ai.deltaY,ac.min_height_px),ac.max_height_px);$(ac.tiles_div).css("height",ag);ac.visible_height_px=(ac.max_height_px===ag?0:ag);ac.on_resize()}).bind("dragend",function(ag,ah){ac.tile_cache.clear();ae=false;if(!af){ad.hide()}ac.config.get("values").height=ac.visible_height_px;ac.changed()}).appendTo(ac.container_div)},set_display_modes:function(af,ai){this.display_modes=af;this.mode=(ai?ai:(this.config&&this.config.get("values").mode?this.config.get("values").mode:this.display_modes[0]));this.action_icons.mode_icon.attr("title","Set display mode (now: "+this.mode+")");var ad=this,ag={};for(var ae=0,ac=ad.display_modes.length;ae<ac;ae++){var ah=ad.display_modes[ae];ag[ah]=function(aj){return function(){ad.change_mode(aj);ad.icons_div.show();ad.container_div.mouseleave(function(){ad.icons_div.hide()})}}(ah)}make_popupmenu(this.action_icons.mode_icon,ag)},build_action_icons:function(){r.prototype.build_action_icons.call(this,this.action_icons_def);if(this.display_modes!==undefined){this.set_display_modes(this.display_modes)}},hide_contents:function(){this.tiles_div.hide();this.container_div.find(".yaxislabel, .track-resize").hide()},show_contents:function(){this.tiles_div.show();this.container_div.find(".yaxislabel, .track-resize").show();this.request_draw()},get_type:function(){if(this instanceof W){return"LabelTrack"}else{if(this instanceof D){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof T){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof d){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.tiles_div.css("height","auto");ad.tiles_div.text("").children().remove();ad.container_div.removeClass("nodata error pending");if(!ad.dataset.id){return}var ac=$.Deferred(),af={hda_ldda:ad.dataset.get("hda_ldda"),data_type:this.dataset_check_type,chrom:ad.view.chrom,retry:ae};$.getJSON(this.dataset.url(),af,function(ag){if(!ag||ag==="error"||ag.kind==="error"){ad.container_div.addClass("error");ad.tiles_div.text(o);if(ag.message){ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("View error").click(function(){Galaxy.modal.show({title:"Trackster Error",body:"<pre>"+ag.message+"</pre>",buttons:{Close:function(){Galaxy.modal.hide()}}})}));ad.tiles_div.append($("<span/>").text(" "));ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("Try again").click(function(){ad.init(true)}))}}else{if(ag==="no converter"){ad.container_div.addClass("error");ad.tiles_div.text(J)}else{if(ag==="no data"||(ag.data!==undefined&&(ag.data===null||ag.data.length===0))){ad.container_div.addClass("nodata");ad.tiles_div.text(G)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(w);setTimeout(function(){ad.init()},ad.data_query_wait)}else{if(ag==="data"||ag.status==="data"){if(ag.valid_chroms){ad.valid_chroms=ag.valid_chroms;ad.update_icons()}ad.tiles_div.text(U);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when.apply($,ad.predraw_init()).done(function(){ac.resolve();ad.container_div.removeClass("nodata error pending");ad.request_draw()})}else{ac.resolve()}}}}}}});this.update_icons();return ac},predraw_init:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){ac.container_div.addClass("line-track");var af=ad.data;if(af&&af.min&&af.max){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.config.set_param_default_value("min_value",ae);ac.config.set_param_default_value("max_value",ag);ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},get_drawables:function(){return this}});var N=function(ae,ad,ag){g.call(this,ae,ad,ag);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in ag?ag.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=(ag.tool?new s(ab.extend(ag.tool,{track:this,tool_state:ag.tool_state})):null);this.tile_cache=new y.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){var af=new aa({model:this.tool});af.render();this.dynamic_tool_div=af.$el;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);if(!this.prefs.content_visible){this.tiles_div.hide()}this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(ag.mode){this.change_mode(ag.mode)}};q(N.prototype,r.prototype,g.prototype,{action_icons_def:g.prototype.action_icons_def.concat([{name:"show_more_rows_icon",title:"To minimize track height, not all feature rows are displayed. Click to display more rows.",css_class:"exclamation",on_click_fn:function(ac){$(".tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw({clear_tile_cache:true})},hide:true}]),copy:function(ac){var ad=this.to_dict();q(ad,{data_manager:this.data_manager});var ae=new this.constructor(this.view,ac,ad);ae.change_mode(this.mode);ae.enabled=this.enabled;return ae},set_filters_manager:function(ac){this.filters_manager=ac;this.header_div.after(this.filters_manager.parent_div)},to_dict:function(){return{track_type:this.get_type(),dataset:{id:this.dataset.id,hda_ldda:this.dataset.get("hda_ldda")},prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},set_min_max:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){var af=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.get("values").mode=ad;if(ad==="Auto"){this.data_manager.clear()}ac.request_draw({clear_tile_cache:true});this.action_icons.mode_icon.attr("title","Set display mode (now: "+ac.mode+")");return ac},update_icons:function(){var ac=this;if(ac.filters_available){ac.action_icons.filters_icon.show()}else{ac.action_icons.filters_icon.hide()}if(ac.tool){ac.action_icons.tools_icon.show();ac.action_icons.param_space_viz_icon.show()}else{ac.action_icons.tools_icon.hide();ac.action_icons.param_space_viz_icon.hide()}},_gen_tile_cache_key:function(ad,ac){return ad+"_"+ac},request_draw:function(ac){if(ac&&ac.clear_tile_cache){this.tile_cache.clear()}this.view.request_redraw(ac,this)},before_draw:function(){this.max_height_px=0},_draw:function(aq){if(!this.can_draw()){return}var an=aq&&aq.clear_after,al=this.view.low,ag=this.view.high,aj=ag-al,ad=this.view.container.width(),ap=this.view.resolution_px_b,af=1/ap;if(this.is_overview){al=this.view.max_low;ag=this.view.max_high;ap=ad/(view.max_high-view.max_low);af=1/ap}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(af*S)),ak,am,ah,ai=[],ao=[];while((ac*S*af)<ag){ak=Math.floor(ac*S*af);am=new y.GenomeRegion({chrom:this.view.chrom,start:ak,end:Math.min(ak+Math.ceil(S*af),this.view.max_high)});ah=this.draw_helper(am,ap,aq);ai.push(ah);$.when(ah).then(function(ar){ao.push(ar)});ac+=1}if(!an){this.tiles_div.children(".remove").removeClass("remove").remove()}var ae=this;$.when.apply($,ai).then(function(){ae.tiles_div.children(".remove").remove();ao=ab.filter(ao,function(ar){return ar!==null});if(ao.length!==0){ae.postdraw_actions(ao,ad,ap,an)}})},_add_yaxis_label:function(af,ah){var ad=this,ag=(af==="max"?"top":"bottom"),ai=(af==="max"?"max":"min"),ac=(af==="max"?"max_value":"min_value"),ae=this.container_div.find(".yaxislabel."+ag);ah=ah||function(){ad.request_draw({clear_tile_cache:true})};if(ae.length!==0){ae.text(ad.prefs[ac])}else{ae=$("<div/>").text(ad.prefs[ac]).make_text_editable({num_cols:12,on_finish:function(aj){$(".tooltip").remove();ad.config.set_param_value(ac,aj);ah()},help_text:"Set "+ai+" value"}).addClass("yaxislabel "+ag).css("color",this.prefs.label_color);this.container_div.prepend(ae)}},postdraw_actions:function(af,ag,ai,ac){var ae=ab.filter(af,function(aj){return(aj instanceof M)});if(ae.length>0){this.max_height_px=0;var ad=this;ab.each(af,function(aj){if(!(aj instanceof M)){aj.html_elt.remove();ad.draw_helper(aj.region,ai,{force:true,mode:"Coverage"})}});ad._add_yaxis_label("max")}else{this.container_div.find(".yaxislabel").remove();var ah=ab.find(af,function(aj){return aj.has_icons});if(ah){ab.each(af,function(aj){if(!aj.has_icons){aj.html_elt.css("padding-top",F)}})}}},get_mode:function(ac){return this.mode},update_auto_mode:function(ac){},_get_drawables:function(){return[this]},draw_helper:function(al,an,ao){if(!ao){ao={}}var ad=ao.force,ai=ao.mode||this.mode,af=1/an,ae=this,ag=this._get_drawables(),am=this._gen_tile_cache_key(an,al),ah=function(ap){return(ap&&"track" in ap)};var aj=(ad?undefined:ae.tile_cache.get_elt(am));if(aj){if(ah(aj)){ae.show_tile(aj,an)}return aj}if(ao.data_fetch===false){return null}var ak=function(){var ap=(ab.find(C,function(ar){return ar===ai})?"Coverage":ai);var aq=ab.map(ag,function(ar){return ar.data_manager.get_data(al,ap,af,ae.data_url_extra_params)});if(view.reference_track){aq.push(view.reference_track.data_manager.get_data(al,ai,af,view.reference_track.data_url_extra_params))}return aq};var ac=$.Deferred();ae.tile_cache.set_elt(am,ac);$.when.apply($,ak()).then(function(){var ap=ak(),av=ap,aB;if(view.reference_track){aB=view.reference_track.data_manager.subset_entry(ap.pop(),al)}var aw=[],at=[];ab.each(ag,function(aG,aD){var aF=aG.mode,aE=av[aD];if(aF==="Auto"){aF=aG.get_mode(aE);aG.update_auto_mode(aF)}aw.push(aF);at.push(aG.get_canvas_height(aE,aF,an,aq))});var au=ae.view.canvas_manager.new_canvas(),ax=al.get("start"),aC=al.get("end"),ar=0,aq=Math.ceil((aC-ax)*an)+ae.left_offset,az=ab.max(at),ay;au.width=aq;au.height=(ao.height||az);var aA=au.getContext("2d");aA.translate(ae.left_offset,0);if(ag.length>1){aA.globalAlpha=0.5;aA.globalCompositeOperation="source-over"}ab.each(ag,function(aE,aD){ay=aE.draw_tile(av[aD],aA,aw[aD],al,an,aB)});if(ay!==undefined){ae.tile_cache.set_elt(am,ay);ae.show_tile(ay,an)}ac.resolve(ay)});return ac},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_line_track_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.LinePainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new M(this,ag,ai,af,ac.data)},draw_tile:function(ac,ad,ag,af,ah,ae){},show_tile:function(ae,ah){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ah;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{this.tiles_div.append(ac)}ac.css("height","auto");this.max_height_px=Math.max(this.max_height_px,ac.height());ac.parent().children().css("height",this.max_height_px+"px");var af=this.max_height_px;if(this.visible_height_px!==0){af=Math.min(this.max_height_px,this.visible_height_px)}this.tiles_div.css("height",af+"px")},tool_region_and_parameters_str:function(af){var ac=this,ae=(af!==undefined?af.toString():"all"),ad=ab.values(ac.tool.get_inputs_dict()).join(", ");return" - region=["+ae+"], parameters=["+ad+"]"},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="bigwig"}else{if(ac.dataset_type==="bigwig"||ac.extra_info==="no_detail"){return false}else{return true}}}},can_subset:function(ac){if(ac.message||ac.extra_info==="no_detail"){return false}else{if(ac.dataset_type==="bigwig"){return(ac.data[1][0]-ac.data[0][0]===1)}}return true},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state"}});var W=function(ad,ac){var ae={resize:false};g.call(this,ad,ac,ae);this.container_div.addClass("label-track")};q(W.prototype,g.prototype,{build_header_div:function(){},init:function(){this.enabled=true},predraw_init:function(){},_draw:function(ag){var ae=this.view,af=ae.high-ae.low,aj=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/aj)*aj,ah=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ai=(ac-ae.low)/af*ah;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ai-1}));ac+=aj}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){N.call(this,ad,ac,ag);this.drawables=[];if("drawables" in ag){var af;for(var ae=0;ae<ag.drawables.length;ae++){af=ag.drawables[ae];this.drawables[ae]=p(af,ad,null);if(af.left_offset>this.left_offset){this.left_offset=af.left_offset}}this.enabled=true}ab.each(this.drawables,function(ah){if(ah instanceof d||ah instanceof T){ah.change_mode("Coverage")}});this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,N.prototype,{display_modes:C,action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_group()}}].concat(N.prototype.action_icons_def),to_dict:A.prototype.to_dict,add_drawable:A.prototype.add_drawable,unpack_drawables:A.prototype.unpack_drawables,change_mode:function(ac){N.prototype.change_mode.call(this,ac);for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].change_mode(ac)}},init:function(){var ae=[];for(var ad=0;ad<this.drawables.length;ad++){ae.push(this.drawables[ad].init())}var ac=this;$.when.apply($,ae).then(function(){ac.enabled=true;ac.request_draw()})},update_icons:function(){this.action_icons.filters_icon.hide();this.action_icons.tools_icon.hide();this.action_icons.param_space_viz_icon.hide()},can_draw:r.prototype.can_draw,_get_drawables:function(){return this.drawables},show_group:function(){var af=new P(this.view,this.container,{name:this.prefs.name}),ac;for(var ae=0;ae<this.drawables.length;ae++){ac=this.drawables[ae];ac.update_icons();af.add_drawable(ac);ac.container=af;af.content_div.append(ac.container_div)}var ad=this.container.replace_drawable(this,af,true);af.request_draw({clear_tile_cache:true})},before_draw:function(){N.prototype.before_draw.call(this);var ad=ab.min(ab.map(this.drawables,function(ae){return ae.prefs.min_value})),ac=ab.max(ab.map(this.drawables,function(ae){return ae.prefs.max_value}));this.prefs.min_value=ad;this.prefs.max_value=ac;ab.each(this.drawables,function(ae){ae.prefs.min_value=ad;ae.prefs.max_value=ac})},update_all_min_max:function(){var ac=this;ab.each(this.drawables,function(ad){ad.prefs.min_value=ac.prefs.min_value;ad.prefs.max_value=ac.prefs.max_value});this.request_draw({clear_tile_cache:true})},postdraw_actions:function(ai,ac,al,ah){N.prototype.postdraw_actions.call(this,ai,ac,al,ah);var ag=-1,ae;for(ae=0;ae<ai.length;ae++){var aj=ai[ae].html_elt.find("canvas").height();if(aj>ag){ag=aj}}for(ae=0;ae<ai.length;ae++){var af=ai[ae];if(af.html_elt.find("canvas").height()!==ag){this.draw_helper(af.region,al,{force:true,height:ag});af.html_elt.remove()}}var ad=this,ak=function(){ad.update_all_min_max()};this._add_yaxis_label("min",ak);this._add_yaxis_label("max",ak)}});var D=function(ac){N.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});this.left_offset=ac.canvas_manager.char_width_px;this.container_div.addClass("reference-track");this.data_url=galaxy_config.root+"api/genomes/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new y.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(D.prototype,r.prototype,N.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"height",type:"int",default_value:13,hidden:true}]),build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},predraw_init:function(){},can_draw:r.prototype.can_draw,draw_helper:function(ad,ae,ac){if(ae>this.view.canvas_manager.char_width_px){this.tiles_div.show();return N.prototype.draw_helper.call(this,ad,ae,ac)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(ae,ak,af,ah,al){var ad=this.data_manager.subset_entry(ae,ah),aj=ad.data;var ac=ak.canvas;ak.font=ak.canvas.manager.default_font;ak.textAlign="center";for(var ag=0,ai=aj.length;ag<ai;ag++){ak.fillStyle=this.view.get_base_color(aj[ag]);ak.fillText(aj[ag],Math.floor(ag*al),10)}return new c(this,ah,al,ac,ad)}});var h=function(ad,ac,ae){this.mode="Histogram";N.call(this,ad,ac,ae)};q(h.prototype,r.prototype,N.prototype,{display_modes:C,config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Color",type:"color",default_value:l.get_random_color()},{key:"min_value",label:"Min Value",type:"float",default_value:undefined},{key:"max_value",label:"Max Value",type:"float",default_value:undefined},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:30,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},before_draw:function(){},draw_tile:function(ac,ad,af,ae,ag){return this._draw_line_track_tile(ac,ad,af,ae,ag)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)},postdraw_actions:function(ad,ae,af,ac){this._add_yaxis_label("max");this._add_yaxis_label("min")}});var t=function(ad,ac,ae){this.mode="Heatmap";N.call(this,ad,ac,ae)};q(t.prototype,r.prototype,N.prototype,{display_modes:["Heatmap"],config_params:ab.union(r.prototype.config_params,[{key:"pos_color",label:"Positive Color",type:"color",default_value:"#FF8C00"},{key:"neg_color",label:"Negative Color",type:"color",default_value:"#4169E1"},{key:"min_value",label:"Min Value",type:"float",default_value:-1},{key:"max_value",label:"Max Value",type:"float",default_value:1},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:500,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new c(this,ag,ai,af,ac.data)}});var d=function(ad,ac,ae){N.call(this,ad,ac,ae);this.container_div.addClass("feature-track");this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(d.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true,help:"Show the number of items in each bin when drawing summary histogram"},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"connector_style",label:"Connector style",type:"select",default_value:"fishbones",options:[{label:"Line with arrows",value:"fishbone"},{label:"Arcs",value:"arcs"}]},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.set_painter_from_config();this.request_draw({clear_tile_cache:true})},set_painter_from_config:function(){if(this.config.get("values").connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},postdraw_actions:function(am,ae,an,al){N.prototype.postdraw_actions.call(this,am,ae,an,al);var ag=this,ah;if(ag.filters_manager){var af=ag.filters_manager.filters,aj;for(aj=0;aj<af.length;aj++){af[aj].update_ui_elt()}var ai=false,ak,ad;for(ah=0;ah<am.length;ah++){if(am[ah].data.length){ak=am[ah].data[0];for(aj=0;aj<af.length;aj++){ad=af[aj];if(ad.applies_to(ak)&&ad.min!==ad.max){ai=true;break}}}}if(ag.filters_available!==ai){ag.filters_available=ai;if(!ag.filters_available){ag.filters_manager.hide()}ag.update_icons()}}if(am[0] instanceof O){var ac=true;for(ah=0;ah<am.length;ah++){if(!am[ah].all_slotted){ac=false;break}}if(!ac){this.action_icons.show_more_rows_icon.show()}else{this.action_icons.show_more_rows_icon.hide()}}else{this.action_icons.show_more_rows_icon.hide()}},update_auto_mode:function(ac){if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}this.action_icons.mode_icon.attr("title","Set display mode (now: Auto/"+ac+")")}},incremental_slots:function(ag,ac,af){var ad=this.view.canvas_manager.dummy_context,ae=this.slotters[ag];if(!ae||(ae.mode!==af)){ae=new (u.FeatureSlotter)(ag,af,B,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.extra_info==="no_detail"||this.is_overview){mode="no_detail"}else{if(this.view.high-this.view.low>I){mode="Squish"}else{mode="Pack"}}return mode},get_canvas_height:function(ac,ag,ah,ad){if(ag==="Coverage"||ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var af=this.incremental_slots(ah,ac.data,ag);var ae=new (this.painter)(null,null,null,this.prefs,ag);return Math.max(this.min_height_px,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,af,aj,ae){var ap=this,ad=aq.canvas,ax=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(am.dataset_type==="bigwig"){return this._draw_line_track_tile(am,aq,ao,af,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var ar=0,au=am.data.length;ar<au;ar++){var ah=am.data[ar];var at=false;var al;for(var aw=0,aB=ak.length;aw<aB;aw++){al=ak[aw];al.update_attrs(ah);if(!al.keep(ah)){at=true;break}}if(!at){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aA=(this.filters_manager.alpha_filter?new E(this.filters_manager.alpha_filter):null),ay=(this.filters_manager.height_filter?new E(this.filters_manager.height_filter):null),az=new (this.painter)(ai,ax,ac,this.prefs,ao,aA,ay,ae,function(aC){return ap.view.get_base_color(aC)});var av=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){av=az.draw(aq,ad.width,ad.height,aj,an);av.translation=-ag}return new O(ap,af,aj,ad,am.data,ao,am.message,all_slotted,av)}});var Z=function(ad,ac,ae){N.call(this,ad,ac,ae);this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Histogram color",type:"color",default_value:l.get_random_color()},{key:"show_sample_data",label:"Show sample data",type:"bool",default_value:true},{key:"show_labels",label:"Show summary and sample labels",type:"bool",default_value:true},{key:"summary_height",label:"Locus summary height",type:"float",default_value:20},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,af,ah,ag,ai){if(ac.dataset_type==="bigwig"){return this._draw_line_track_tile(ac,af,"Histogram",ag,ai)}else{var ae=this.view,ad=new (this.painter)(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah,function(aj){return ae.get_base_color(aj)});ad.draw(af,af.canvas.width,af.canvas.height,ai);return new c(this,ag,ai,af.canvas,ac.data)}},get_canvas_height:function(ac,ag,ah,ae){if(ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var ad=(this.dataset.get_metadata("sample_names")?this.dataset.get_metadata("sample_names").length:0);if(ad===0&&ac.data.length!==0){ad=ac.data[0][7].match(/,/g);if(ad===null){ad=1}else{ad=ad.length+1}}var af=new (this.painter)(null,null,null,this.prefs,ag);return af.get_required_height(ad)}},predraw_init:function(){var ac=[g.prototype.predraw_init.call(this)];if(!this.dataset.get_metadata("sample_names")){ac.push(this.dataset.fetch())}return ac},postdraw_actions:function(ag,ah,aj,ad){N.prototype.postdraw_actions.call(this,ag,ah,aj,ad);var af=ab.filter(ag,function(ak){return(ak instanceof M)});var ae=this.dataset.get_metadata("sample_names");if(af.length===0&&this.prefs.show_labels&&ae){var ac;if(this.container_div.find(".yaxislabel.variant").length===0){ac=this.prefs.summary_height/2;this.tiles_div.prepend($("<div/>").text("Summary").addClass("yaxislabel variant top").css({"font-size":ac+"px",top:(this.prefs.summary_height-ac)/2+"px"}));if(this.prefs.show_sample_data){var ai=ae.join("<br/>");this.tiles_div.prepend($("<div/>").html(ai).addClass("yaxislabel variant top sample").css({top:this.prefs.summary_height+2,}))}}ac=(this.mode==="Squish"?5:10)+"px";$(this.tiles_div).find(".sample").css({"font-size":ac,"line-height":ac});$(this.tiles_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel.variant").remove()}}});var T=function(ad,ac,ae){d.call(this,ad,ac,ae);this.painter=(ad.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(T.prototype,r.prototype,N.prototype,d.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block and sense strand color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_insertions",label:"Show insertions",type:"bool",default_value:false},{key:"show_differences",label:"Show differences only",type:"bool",default_value:true},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})}});var e={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:d,LineTrack:h,ReadTrack:T,VariantTrack:Z,VcfTrack:Z};var p=function(ae,ad,ac){if("copy" in ae){return ae.copy(ac)}else{var af=ae.obj_type;if(!af){af=ae.track_type}return new e[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:d,DiagonalHeatmapTrack:t,ReadTrack:T,VariantTrack:Z,CompositeTrack:f,object_from_template:p}});
\ No newline at end of file
diff -r 3d138ced1f26c810a24bead0aa8fa6d8a65a7812 -r 2f0053f5952e9b93ded01fcd24ed87783dedc698 static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -3384,9 +3384,11 @@
}
// -- Update track, tile heights based on new tile. --
+
+ tile_element.css('height', 'auto');
- // Update max height based on current tile's canvas.
- this.max_height_px = Math.max(this.max_height_px, $(tile.canvas).height());
+ // Update max height based on current tile's height.
+ this.max_height_px = Math.max(this.max_height_px, tile_element.height());
// Update height for all tiles based on max height.
tile_element.parent().children().css("height", this.max_height_px + "px");
https://bitbucket.org/galaxy/galaxy-central/commits/8ae19975dd33/
Changeset: 8ae19975dd33
User: jgoecks
Date: 2013-10-22 02:59:36
Summary: Automated merge of next-stable
Affected #: 2 files
diff -r 100a64a1d85cbb582bd83ab9bbdd6cbd73a566f2 -r 8ae19975dd333c6b4b4c15f93a0350a24f3c10db static/scripts/packed/viz/trackster/tracks.js
--- a/static/scripts/packed/viz/trackster/tracks.js
+++ b/static/scripts/packed/viz/trackster/tracks.js
@@ -1,1 +1,1 @@
-define(["libs/underscore","viz/visualization","viz/trackster/util","viz/trackster/slotting","viz/trackster/painters","viz/trackster/filters","mvc/data","mvc/tools"],function(ab,y,l,u,L,i,X,R){var q=ab.extend;var n={};var k=function(ac,ad){n[ac.attr("id")]=ad};var m=function(ac,ae,ag,af){ag=".group";var ad={};n[ac.attr("id")]=af;ac.bind("drag",{handle:"."+ae,relative:true},function(ao,ap){var an=$(this),at=$(this).parent(),ak=at.children(),am=n[$(this).attr("id")],aj,ai,aq,ah,al;ai=$(this).parents(ag);if(ai.length!==0){aq=ai.position().top;ah=aq+ai.outerHeight();var ar=n[ai.attr("id")];if(ap.offsetY<aq){$(this).insertBefore(ai);ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);ar.remove_drawable(am);ar.container.add_drawable(am);return}}}ai=null;for(al=0;al<ak.length;al++){aj=$(ak.get(al));aq=aj.position().top;ah=aq+aj.outerHeight();if(aj.is(ag)&&this!==aj.get(0)&&ap.offsetY>=aq&&ap.offsetY<=ah){if(ap.offsetY-aq<ah-ap.offsetY){aj.find(".content-div").prepend(this)}else{aj.find(".content-div").append(this)}if(am.container){am.container.remove_drawable(am)}n[aj.attr("id")].add_drawable(am);return}}for(al=0;al<ak.length;al++){aj=$(ak.get(al));if(ap.offsetY<aj.position().top&&!(aj.hasClass("reference-track")||aj.hasClass("intro"))){break}}if(al===ak.length){if(this!==ak.get(al-1)){at.append(this);n[at.attr("id")].move_drawable(am,al)}}else{if(this!==ak.get(al)){$(this).insertBefore(ak.get(al));n[at.attr("id")].move_drawable(am,(ap.deltaY>0?al-1:al))}}}).bind("dragstart",function(){ad["border-top"]=ac.css("border-top");ad["border-bottom"]=ac.css("border-bottom");$(this).css({"border-top":"1px solid blue","border-bottom":"1px solid blue"})}).bind("dragend",function(){$(this).css(ad)})};var F=20,B=100,I=12000,S=400,K=5000,x=100,o="Cannot display dataset due to an error. ",J="A converter for this dataset is not installed. Please check your datatypes_conf.xml file.",G="No data for this chrom/contig.",w="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",z="Tool cannot be rerun: ",b="Loading data...",U="Ready for display",Q=10,H=20,C=["Histogram","Line","Filled","Intensity"];function V(ad,ac){if(!ac){ac=0}var ae=Math.pow(10,ac);return Math.round(ad*ae)/ae}var r=function(ad,ac,af){if(!r.id_counter){r.id_counter=0}this.id=r.id_counter++;this.view=ad;this.container=ac;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.config=new j({params:this.config_params,onchange:this.config_onchange,saved_values:af.prefs});this.prefs=this.config.get("values");if(!this.prefs.name){this.prefs.name=af.name}if(this.config_onchange){this.config.on("change:values",this.config_onchange,this)}this.container_div=this.build_container_div();this.header_div=this.build_header_div();if(this.header_div){this.container_div.append(this.header_div);this.icons_div=$("<div/>").css("float","left").hide().appendTo(this.header_div);this.build_action_icons(this.action_icons_def);this.header_div.append($("<div style='clear: both'/>"));this.header_div.dblclick(function(ag){ag.stopPropagation()});var ae=this;this.container_div.hover(function(){ae.icons_div.show()},function(){ae.icons_div.hide()});$("<div style='clear: both'/>").appendTo(this.container_div)}};r.prototype.action_icons_def=[{name:"toggle_icon",title:"Hide/show content",css_class:"toggle",on_click_fn:function(ac){if(ac.prefs.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.prefs.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.prefs.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var ac=new a({model:ad.config});ac.render()}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".tooltip").remove();ac.remove()}}];q(r.prototype,{config_params:[{key:"name",label:"Name",type:"text",default_value:""},{key:"content_visible",type:"bool",default_value:true,hidden:true}],config_onchange:function(){this.track.set_name(this.track.config.get("values").name)},init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.prefs.content_visible){return true}return false},request_draw:function(){},_draw:function(ac){},to_dict:function(){},set_name:function(ac){this.old_name=this.prefs.name;this.prefs.name=ac;this.name_div.text(this.prefs.name)},revert_name:function(){if(this.old_name){this.prefs.name=this.old_name;this.name_div.text(this.prefs.name)}},remove:function(){this.changed();this.container.remove_drawable(this);var ac=this.view;this.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})},build_container_div:function(){},build_header_div:function(){},add_action_icon:function(ad,ai,ah,ag,ac,af){var ae=this;this.action_icons[ad]=$("<a/>").attr("title",ai).addClass("icon-button").addClass(ah).tooltip().click(function(){ag(ae)}).appendTo(this.icons_div);if(af){this.action_icons[ad].hide()}},build_action_icons:function(ac){var ae;for(var ad=0;ad<ac.length;ad++){ae=ac[ad];this.add_action_icon(ae.name,ae.title,ae.css_class,ae.on_click_fn,ae.prepend,ae.hide)}},update_icons:function(){},hide_contents:function(){},show_contents:function(){},get_drawables:function(){}});var A=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(A.prototype,r.prototype,{unpack_drawables:function(ae){this.drawables=[];var ad;for(var ac=0;ac<ae.length;ac++){ad=p(ae[ac],this.view,this);this.add_drawable(ad)}},init:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].init()}},_draw:function(ac){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad]._draw(ac)}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{prefs:this.prefs,obj_type:this.obj_type,drawables:ad}},add_drawable:function(ac){this.drawables.push(ac);ac.container=this;this.changed()},add_drawable_before:function(ae,ac){this.changed();var ad=this.drawables.indexOf(ac);if(ad!==-1){this.drawables.splice(ad,0,ae);return true}return false},replace_drawable:function(ae,ac,ad){var af=this.drawables.indexOf(ae);if(af!==-1){this.drawables[af]=ac;if(ad){ae.container_div.replaceWith(ac.container_div)}this.changed()}return af},remove_drawable:function(ad){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);ad.container=null;this.changed();return true}return false},move_drawable:function(ad,ae){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);this.drawables.splice(ae,0,ad);this.changed();return true}return false},get_drawables:function(){return this.drawables},get_tracks:function(af){var ac=this.drawables.slice(0),ad=[],ae;while(ac.length!==0){ae=ac.shift();if(ae instanceof af){ad.push(ae)}else{if(ae.drawables){ac=ac.concat(ae.drawables)}}}return ad}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});A.call(this,ad,ac,af);this.content_div=$("<div/>").addClass("content-div").attr("id","group_"+this.id+"_content_div").appendTo(this.container_div);k(this.container_div,this);k(this.content_div,this);m(this.container_div,this.drag_handle_class,".group",this);this.filters_manager=new i.FiltersManager(this);this.header_div.after(this.filters_manager.parent_div);this.saved_filters_managers=[];if("drawables" in af){this.unpack_drawables(af.drawables)}if("filters" in af){var ae=this.filters_manager;this.filters_manager=new i.FiltersManager(this,af.filters);ae.parent_div.replaceWith(this.filters_manager.parent_div);if(af.filters.visible){this.setup_multitrack_filtering()}}};q(P.prototype,r.prototype,A.prototype,{action_icons_def:[r.prototype.action_icons_def[0],r.prototype.action_icons_def[1],{name:"composite_icon",title:"Show composite track",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_composite_track()}},{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters();ac._restore_filter_managers()}else{ac.setup_multitrack_filtering();ac.request_draw({clear_tile_cache:true})}ac.filters_manager.toggle()}},r.prototype.action_icons_def[2]],build_container_div:function(){var ac=$("<div/>").addClass("group").attr("id","group_"+this.id);if(this.container){this.container.content_div.append(ac)}return ac},build_header_div:function(){var ac=$("<div/>").addClass("track-header");ac.append($("<div/>").addClass(this.drag_handle_class));this.name_div=$("<div/>").addClass("track-name").text(this.prefs.name).appendTo(ac);return ac},hide_contents:function(){this.tiles_div.hide()},show_contents:function(){this.tiles_div.show();this.request_draw()},update_icons:function(){var ae=this.drawables.length;if(ae===0){this.action_icons.composite_icon.hide();this.action_icons.filters_icon.hide()}else{if(ae===1){if(this.drawables[0] instanceof f){this.action_icons.composite_icon.show()}this.action_icons.filters_icon.hide()}else{var al,ak,ai,ao=true,ag=this.drawables[0].get_type(),ac=0;for(al=0;al<ae;al++){ai=this.drawables[al];if(ai.get_type()!==ag){can_composite=false;break}if(ai instanceof d){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".tooltip").remove()}if(ac>1&&ac===this.drawables.length){var ap={},ad;ai=this.drawables[0];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];ap[ad.name]=[ad]}for(al=1;al<this.drawables.length;al++){ai=this.drawables[al];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];if(ad.name in ap){ap[ad.name].push(ad)}}}this.filters_manager.remove_all();var af,ah,aj,am;for(var an in ap){af=ap[an];if(af.length===ac){ah=new i.NumberFilter({name:af[0].name,index:af[0].index});this.filters_manager.add_filter(ah)}}if(this.filters_manager.filters.length>0){this.action_icons.filters_icon.show()}else{this.action_icons.filters_icon.hide()}}else{this.action_icons.filters_icon.hide()}}}},_restore_filter_managers:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].filters_manager=this.saved_filters_managers[ac]}this.saved_filters_managers=[]},setup_multitrack_filtering:function(){if(this.filters_manager.filters.length>0){this.saved_filters_managers=[];for(var ac=0;ac<this.drawables.length;ac++){drawable=this.drawables[ac];this.saved_filters_managers.push(drawable.filters_manager);drawable.filters_manager=this.filters_manager}}this.filters_manager.init_filters()},show_composite_track:function(){var ad=new f(this.view,this.view,{name:this.prefs.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ad,true);ad.request_draw()},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){A.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(A.prototype.to_dict.call(this),{filters:this.filters_manager.to_dict()});if(this.filters_manager.visible()){this.setup_multitrack_filtering()}return ac},request_draw:function(ac){ab.each(this.drawables,function(ad){ad.request_draw(ac)})}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});A.call(this,"View",ac.container,ac);this.chrom=null;this.vis_id=ac.vis_id;this.dbkey=ac.dbkey;this.label_tracks=[];this.tracks_to_be_redrawn=[];this.max_low=0;this.max_high=0;this.zoom_factor=3;this.min_separation=30;this.has_changes=false;this.load_chroms_deferred=null;this.render();this.canvas_manager=new y.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new j({track:this,params:[{key:"a_color",label:"A Color",type:"color",default_value:"#FF0000"},{key:"c_color",label:"C Color",type:"color",default_value:"#00FF00"},{key:"g_color",label:"G Color",type:"color",default_value:"#0000FF"},{key:"t_color",label:"T Color",type:"color",default_value:"#FF00FF"},{key:"n_color",label:"N Color",type:"color",default_value:"#AAAAAA"}],saved_values:ac.prefs,onchange:function(){track.request_redraw({clear_tile_cache:true})}})},render:function(){this.requested_redraw=false;var ae=this.container,ac=this;this.top_container=$("<div/>").addClass("top-container").appendTo(ae);this.browser_content_div=$("<div/>").addClass("content").css("position","relative").appendTo(ae);this.bottom_container=$("<div/>").addClass("bottom-container").appendTo(ae);this.top_labeltrack=$("<div/>").addClass("top-labeltrack").appendTo(this.top_container);this.viewport_container=$("<div/>").addClass("viewport-container").attr("id","viewport-container").appendTo(this.browser_content_div);this.content_div=this.viewport_container;k(this.viewport_container,ac);this.intro_div=$("<div/>").addClass("intro").appendTo(this.viewport_container).hide();var af=$("<div/>").text("Add Datasets to Visualization").addClass("action-button").appendTo(this.intro_div).click(function(){y.select_datasets(galaxy_config.root+"visualization/list_current_history_datasets",galaxy_config.root+"api/datasets",{"f-dbkey":ac.dbkey},function(ag){ab.each(ag,function(ah){ac.add_drawable(p(ah,ac,ac))})})});this.nav_labeltrack=$("<div/>").addClass("nav-labeltrack").appendTo(this.bottom_container);this.nav_container=$("<div/>").addClass("trackster-nav-container").prependTo(this.top_container);this.nav=$("<div/>").addClass("trackster-nav").appendTo(this.nav_container);this.overview=$("<div/>").addClass("overview").appendTo(this.bottom_container);this.overview_viewport=$("<div/>").addClass("overview-viewport").appendTo(this.overview);this.overview_close=$("<a/>").attr("title","Close overview").addClass("icon-button overview-close tooltip").hide().appendTo(this.overview_viewport);this.overview_highlight=$("<div/>").addClass("overview-highlight").hide().appendTo(this.overview_viewport);this.overview_box_background=$("<div/>").addClass("overview-boxback").appendTo(this.overview_viewport);this.overview_box=$("<div/>").addClass("overview-box").appendTo(this.overview_viewport);this.default_overview_height=this.overview_box.height();this.nav_controls=$("<div/>").addClass("nav-controls").appendTo(this.nav);this.chrom_select=$("<select/>").attr({name:"chrom"}).css("width","15em").append("<option value=''>Loading</option>").appendTo(this.nav_controls);var ad=function(ag){if(ag.type==="focusout"||(ag.keyCode||ag.which)===13||(ag.keyCode||ag.which)===27){if((ag.keyCode||ag.which)!==27){ac.go_to($(this).val())}$(this).hide();$(this).val("");ac.location_span.show();ac.chrom_select.show()}};this.nav_input=$("<input/>").addClass("nav-input").hide().bind("keyup focusout",ad).appendTo(this.nav_controls);this.location_span=$("<span/>").addClass("location").attr("original-title","Click to change location").tooltip({placement:"bottom"}).appendTo(this.nav_controls);this.location_span.click(function(){ac.location_span.hide();ac.chrom_select.hide();ac.nav_input.val(ac.chrom+":"+ac.low+"-"+ac.high);ac.nav_input.css("display","inline-block");ac.nav_input.select();ac.nav_input.focus();ac.nav_input.autocomplete({source:function(ai,ag){var aj=[],ah=$.map(ac.get_tracks(d),function(ak){return ak.data_manager.search_features(ai.term).success(function(al){aj=aj.concat(al)})});$.when.apply($,ah).done(function(){ag($.map(aj,function(ak){return{label:ak[0],value:ak[1]}}))})}})});if(this.vis_id!==undefined){this.hidden_input=$("<input/>").attr("type","hidden").val(this.vis_id).appendTo(this.nav_controls)}this.zo_link=$("<a/>").attr("id","zoom-out").attr("title","Zoom out").tooltip({placement:"bottom"}).click(function(){ac.zoom_out();ac.request_redraw()}).appendTo(this.nav_controls);this.zi_link=$("<a/>").attr("id","zoom-in").attr("title","Zoom in").tooltip({placement:"bottom"}).click(function(){ac.zoom_in();ac.request_redraw()}).appendTo(this.nav_controls);this.load_chroms_deferred=this.load_chroms({low:0});this.chrom_select.bind("change",function(){ac.change_chrom(ac.chrom_select.val())});this.browser_content_div.click(function(ag){$(this).find("input").trigger("blur")});this.browser_content_div.bind("dblclick",function(ag){ac.zoom_in(ag.pageX,this.viewport_container)});this.overview_box.bind("dragstart",function(ag,ah){this.current_x=ah.offsetX}).bind("drag",function(ag,ai){var aj=ai.offsetX-this.current_x;this.current_x=ai.offsetX;var ah=Math.round(aj/ac.viewport_container.width()*(ac.max_high-ac.max_low));ac.move_delta(-ah)});this.overview_close.click(function(){ac.reset_overview()});this.viewport_container.bind("draginit",function(ag,ah){if(ag.clientX>ac.viewport_container.width()-16){return false}}).bind("dragstart",function(ag,ah){ah.original_low=ac.low;ah.current_height=ag.clientY;ah.current_x=ah.offsetX}).bind("drag",function(ai,ak){var ag=$(this);var al=ak.offsetX-ak.current_x;var ah=ag.scrollTop()-(ai.clientY-ak.current_height);ag.scrollTop(ah);ak.current_height=ai.clientY;ak.current_x=ak.offsetX;var aj=Math.round(al/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}).bind("mousewheel",function(ai,ak,ah,ag){if(ah){ah*=50;var aj=Math.round(-ah/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}});this.top_labeltrack.bind("dragstart",function(ag,ah){return $("<div />").css({height:ac.browser_content_div.height()+ac.top_labeltrack.height()+ac.nav_labeltrack.height()+1,top:"0px",position:"absolute","background-color":"#ccf",opacity:0.5,"z-index":1000}).appendTo($(this))}).bind("drag",function(ak,al){$(al.proxy).css({left:Math.min(ak.pageX,al.startX)-ac.container.offset().left,width:Math.abs(ak.pageX-al.startX)});var ah=Math.min(ak.pageX,al.startX)-ac.container.offset().left,ag=Math.max(ak.pageX,al.startX)-ac.container.offset().left,aj=(ac.high-ac.low),ai=ac.viewport_container.width();ac.update_location(Math.round(ah/ai*aj)+ac.low,Math.round(ag/ai*aj)+ac.low)}).bind("dragend",function(al,am){var ah=Math.min(al.pageX,am.startX),ag=Math.max(al.pageX,am.startX),aj=(ac.high-ac.low),ai=ac.viewport_container.width(),ak=ac.low;ac.low=Math.round(ah/ai*aj)+ak;ac.high=Math.round(ag/ai*aj)+ak;$(am.proxy).remove();ac.request_redraw()});this.add_label_track(new W(this,{content_div:this.top_labeltrack}));this.add_label_track(new W(this,{content_div:this.nav_labeltrack}));$(window).bind("resize",function(){if(this.resize_timer){clearTimeout(this.resize_timer)}this.resize_timer=setTimeout(function(){ac.resize_window()},500)});$(document).bind("redraw",function(){ac.redraw()});this.reset();$(window).trigger("resize")},get_base_color:function(ac){return this.config.get("values")[ac.toLowerCase()+"_color"]||this.config.get("values").n_color}});q(Y.prototype,A.prototype,{changed:function(){this.has_changes=true},update_intro_div:function(){if(this.drawables.length===0){this.intro_div.show()}else{this.intro_div.hide()}},trigger_navigate:function(ad,af,ac,ag){if(this.timer){clearTimeout(this.timer)}if(ag){var ae=this;this.timer=setTimeout(function(){ae.trigger("navigate",ad+":"+af+"-"+ac)},500)}else{view.trigger("navigate",ad+":"+af+"-"+ac)}},update_location:function(ac,ae){this.location_span.text(commatize(ac)+" - "+commatize(ae));this.nav_input.val(this.chrom+":"+commatize(ac)+"-"+commatize(ae));var ad=view.chrom_select.val();if(ad!==""){this.trigger_navigate(ad,view.low,view.high,true)}},load_chroms:function(ae){ae.num=x;var ac=this,ad=$.Deferred();$.ajax({url:galaxy_config.root+"api/genomes/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){var ah=new D(ac);ac.add_label_track(ah);ac.reference_track=ah}ac.chrom_data=ag.chrom_info;var ak='<option value="">Select Chrom/Contig</option>';for(var aj=0,af=ac.chrom_data.length;aj<af;aj++){var ai=ac.chrom_data[aj].chrom;ak+='<option value="'+ai+'">'+ai+"</option>"}if(ag.prev_chroms){ak+='<option value="previous">Previous '+x+"</option>"}if(ag.next_chroms){ak+='<option value="next">Next '+x+"</option>"}ac.chrom_select.html(ak);ac.chrom_start_index=ag.start_index;ad.resolve(ag.chrom_info)},error:function(){alert("Could not load chroms for this dbkey:",ac.dbkey)}});return ad},change_chrom:function(ah,ad,aj){var ae=this;if(!ae.chrom_data){ae.load_chroms_deferred.then(function(){ae.change_chrom(ah,ad,aj)});return}if(!ah||ah==="None"){return}if(ah==="previous"){ae.load_chroms({low:this.chrom_start_index-x});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+x});return}var ai=$.grep(ae.chrom_data,function(ak,al){return ak.chrom===ah})[0];if(ai===undefined){ae.load_chroms({chrom:ah},function(){ae.change_chrom(ah,ad,aj)});return}else{if(ah!==ae.chrom){ae.chrom=ah;ae.chrom_select.val(ae.chrom);ae.max_high=ai.len-1;ae.reset();for(var ag=0,ac=ae.drawables.length;ag<ac;ag++){var af=ae.drawables[ag];if(af.init){af.init()}}if(ae.reference_track){ae.reference_track.init()}}if(ad&&aj){ae.low=Math.max(ad,0);ae.high=Math.min(aj,ae.max_high)}else{ae.low=0;ae.high=ae.max_high}ae.reset_overview();ae.request_redraw()}},go_to:function(ag){ag=ag.replace(/,/g,"");ag=ag.replace(/:|\-/g," ");var ad=ag.split(/\s+/),af=ad[0],ae=(ad[1]?parseInt(ad[1],10):null),ac=(ad[2]?parseInt(ad[2],10):null);if(!ac){ae=ae-15;ac=ae+15}this.change_chrom(af,ae,ac)},move_fraction:function(ae){var ac=this;var ad=ac.high-ac.low;this.move_delta(ae*ad)},move_delta:function(af){var ac=this;var ae=ac.high-ac.low;if(ac.low-af<ac.max_low){ac.low=ac.max_low;ac.high=ac.max_low+ae}else{if(ac.high-af>ac.max_high){ac.high=ac.max_high;ac.low=ac.max_high-ae}else{ac.high-=af;ac.low-=af}}ac.request_redraw({data_fetch:false});if(this.redraw_on_move_fn){clearTimeout(this.redraw_on_move_fn)}this.redraw_on_move_fn=setTimeout(function(){ac.request_redraw()},200);var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);ac.init();this.changed();this.update_intro_div()},add_label_track:function(ac){ac.view=this;ac.init();this.label_tracks.push(ac)},remove_drawable:function(ae,ad){A.prototype.remove_drawable.call(this,ae);if(ad){var ac=this;ae.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})}},reset:function(){this.low=this.max_low;this.high=this.max_high;this.viewport_container.find(".yaxislabel").remove()},request_redraw:function(ad,ae){var ac=this,af=(ae?[ae]:ac.drawables);ab.each(af,function(ag){var ah=ab.find(ac.tracks_to_be_redrawn,function(ai){return ai[0]===ag});if(ah){ah[1]=ad}else{ac.tracks_to_be_redrawn.push([ag,ad])}});if(!this.requested_redraw){requestAnimationFrame(function(){ac._redraw()});this.requested_redraw=true}},_redraw:function(){this.requested_redraw=false;var ac=this.low,ag=this.high;if(ac<this.max_low){ac=this.max_low}if(ag>this.max_high){ag=this.max_high}var ad=this.high-this.low;if(this.high!==0&&ad<this.min_separation){ag=ac+this.min_separation}this.low=Math.floor(ac);this.high=Math.ceil(ag);this.update_location(this.low,this.high);this.resolution_px_b=this.viewport_container.width()/(this.high-this.low);var af=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ah=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ae=13;this.overview_box.css({left:af,width:Math.max(ae,ah)}).show();if(ah<ae){this.overview_box.css("left",af-(ae-ah)/2)}if(this.overview_highlight){this.overview_highlight.css({left:af,width:ah})}ab.each(this.tracks_to_be_redrawn,function(ak){var ai=ak[0],aj=ak[1];if(ai){ai._draw(aj)}});this.tracks_to_be_redrawn=[];ab.each(this.label_tracks,function(ai){ai._draw()})},zoom_in:function(ad,ae){if(this.max_high===0||this.high-this.low<=this.min_separation){return}var af=this.high-this.low,ag=af/2+this.low,ac=(af/this.zoom_factor)/2;if(ad){ag=ad/this.viewport_container.width()*(this.high-this.low)+this.low}this.low=Math.round(ag-ac);this.high=Math.round(ag+ac);this.changed();this.request_redraw()},zoom_out:function(){if(this.max_high===0){return}var ad=this.high-this.low,ae=ad/2+this.low,ac=(ad*this.zoom_factor)/2;this.low=Math.round(ae-ac);this.high=Math.round(ae+ac);this.changed();this.request_redraw()},resize_window:function(){this.viewport_container.height(this.container.height()-this.top_container.height()-this.bottom_container.height());this.request_redraw()},set_overview:function(ae){if(this.overview_drawable){if(this.overview_drawable.dataset.id===ae.dataset.id){return}this.overview_viewport.find(".track").remove()}var ad=ae.copy({content_div:this.overview_viewport}),ac=this;ad.header_div.hide();ad.is_overview=true;ac.overview_drawable=ad;this.overview_drawable.postdraw_actions=function(){ac.overview_highlight.show().height(ac.overview_drawable.content_div.height());ac.overview_viewport.height(ac.overview_drawable.content_div.height()+ac.overview_box.outerHeight());ac.overview_close.show();ac.resize_window()};ac.overview_drawable.request_draw();this.changed()},reset_overview:function(){$(".tooltip").remove();this.overview_viewport.find(".track-tile").remove();this.overview_viewport.height(this.default_overview_height);this.overview_box.height(this.default_overview_height);this.overview_close.hide();this.overview_highlight.hide();view.resize_window();view.overview_drawable=null}});var s=R.Tool.extend({defaults:{track:null},initialize:function(ac){if(ac.tool_state!==undefined){this.set("hidden",ac.tool_state.hidden)}this.remove_inputs(["data","hidden_data","conditional"])},state_dict:function(ac){return ab.extend(this.get_inputs_dict(),{hidden:!this.is_visible()})}});var v=Backbone.View.extend({events:{"change input":"update_value"},render:function(){var ae=this.$el.addClass("param-row"),af=this.model;var ac=$("<div>").addClass("param-label").text(af.get("label")).appendTo(ae);var ad=$("<div/>").addClass("param-input").html(af.get("html")).appendTo(ae);ad.find(":input").val(af.get("value"));$("<div style='clear: both;'/>").appendTo(ae)},update_value:function(ac){this.model.set_value($(ac.target).val())}});var aa=Backbone.View.extend({initialize:function(ac){this.model.on("change:hidden",this.set_visible,this)},render:function(){var ad=this;tool=this.model,parent_div=this.$el.addClass("dynamic-tool").hide();parent_div.bind("drag",function(ah){ah.stopPropagation()}).click(function(ah){ah.stopPropagation()}).bind("dblclick",function(ah){ah.stopPropagation()}).keydown(function(ah){ah.stopPropagation()});var ae=$("<div class='tool-name'>").appendTo(parent_div).text(tool.get("name"));tool.get("inputs").each(function(ai){var ah=new v({model:ai});ah.render();parent_div.append(ah.$el)});parent_div.find("input").click(function(){$(this).select()});var af=$("<div>").addClass("param-row").appendTo(parent_div);var ag=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(af);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(af);ac.click(function(){ad.run_on_region()});ag.click(function(){ad.run_on_dataset()});if(tool.is_visible()){this.$el.show()}},set_visible:function(){if(this.model.is_visible()){this.$el.show()}else{this.$el.hide()}},update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},run_on_dataset:function(){var ac=this.model;this.run({target_dataset_id:this.model.get("track").dataset.id,action:"rerun",tool_id:ac.id},null,function(ad){Galaxy.modal.show({title:ac.get("name")+" is Running",body:ac.get("name")+" is running on the complete dataset. Tool outputs are in dataset's history.",buttons:{Close:function(){Galaxy.modal.hide()}}})})},run_on_region:function(){var ad=this.model.get("track"),ag=this.model,ai=new y.GenomeRegion({chrom:ad.view.chrom,start:ad.view.low,end:ad.view.high}),aj={target_dataset_id:ad.dataset.id,action:"rerun",tool_id:ag.id,regions:[ai.toJSON()]},ah=ad,al=aj.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ak=new P(view,view,{name:this.prefs.name});var af=ah.container.replace_drawable(ah,ak,false);ak.container_div.insertBefore(ah.view.content_div.children()[af]);ak.add_drawable(ah);ah.container_div.appendTo(ak.content_div);ac=ak}else{ac=ah.container}var ae=new ah.constructor(view,ac,{name:al,hda_ldda:"hda"});ae.init_for_tool_data();ae.change_mode(ah.mode);ae.set_filters_manager(ah.filters_manager.copy(ae));ae.update_icons();ac.add_drawable(ae);ae.tiles_div.text("Starting job.");this.run(aj,ae,function(am){ae.set_dataset(new X.Dataset(am));ae.tiles_div.text("Running job.");ae.init()})},run:function(ac,ae,af){ac.inputs=this.model.get_inputs_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_config.root+"api/tools",data:JSON.stringify(ac),dataType:"json",contentType:"application/json",type:"POST"},interval:2000,success_fn:function(ag){return ag!=="pending"}});$.when(ad.go()).then(function(ag){if(ag==="no converter"){ae.container_div.addClass("error");ae.content_div.text(J)}else{if(ag.error){ae.container_div.addClass("error");ae.content_div.text(z+ag.message)}else{af(ag)}}})}});var E=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};E.prototype.gen_val=function(ac){if(this.filter.high===Number.MAX_VALUE||this.filter.low===-Number.MAX_VALUE||this.filter.low===this.filter.high){return this.default_val}return((parseFloat(ac[this.filter.index])-this.filter.low)/(this.filter.high-this.filter.low))};var j=Backbone.Model.extend({initialize:function(ad){var ac={};ab.each(ad.params,function(ae){ac[ae.key]=ae.default_value});if(ad.saved_values){ab.each(this.get("params"),function(ae){if(ae.key in ad.saved_values){ac[ae.key]=ad.saved_values[ae.key]}})}this.set("values",ac)},set_param_default_value:function(ad,ac){var ae=ab.find(this.get("params"),function(af){return af.key===ad});if(ae){ae.default_value=ac}},set_param_value:function(ac,ad){var ae=ab.find(this.get("params"),function(af){return af.key===ac});if(ae){if(typeof ad==="string"||ad instanceof String){if(ad.trim()===""){ad=ae.default_value}else{if(ae.type==="float"){ad=parseFloat(ad)}else{if(ae.type==="int"){ad=parseInt(ad,10)}}}}}if(this.get("values")[ac]!==ad){this.get("values")[ac]=ad;this.trigger("change:values");return true}else{return false}}});var a=Backbone.View.extend({render:function(){var aj=this.model;var ac=$("<div/>").keydown(function(ak){ak.stopPropagation()});var ai;function ah(ao,ak){for(var at=0;at<ao.length;at++){ai=ao[at];if(ai.hidden){continue}var am="param_"+at;var ax=aj.get("values")[ai.key];var az=$("<div class='form-row' />").appendTo(ak);az.append($("<label />").attr("for",am).text(ai.label+":"));if(ai.type==="bool"){az.append($('<input type="checkbox" />').attr("id",am).attr("name",am).attr("checked",ax))}else{if(ai.type==="text"){az.append($('<input type="text"/>').attr("id",am).val(ax).click(function(){$(this).select()}))}else{if(ai.type==="select"){var av=$("<select />").attr("id",am);for(var aq=0;aq<ai.options.length;aq++){$("<option/>").text(ai.options[aq].label).attr("value",ai.options[aq].value).appendTo(av)}av.val(ax);az.append(av)}else{if(ai.type==="color"){var ay=$("<div/>").appendTo(az),au=$("<input />").attr("id",am).attr("name",am).val(ax).css("float","left").appendTo(ay).click(function(aB){$(".tooltip").removeClass("in");var aA=$(this).siblings(".tooltip").addClass("in");aA.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top+Galaxy.modal.scrollTop()-($(aA).height()/2)+($(this).height()/2)}).show();aA.click(function(aC){aC.stopPropagation()});$(document).bind("click.color-picker",function(){aA.hide();$(document).unbind("click.color-picker")});aB.stopPropagation()}),ar=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(ay).attr("title","Set new random color").tooltip(),aw=$("<div class='tooltip right' style='position: absolute;' />").appendTo(ay).hide(),an=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(aw),al=$("<div class='tooltip-arrow'></div>").appendTo(aw),ap=$.farbtastic(an,{width:100,height:100,callback:au,color:ax});ay.append($("<div/>").css("clear","both"));(function(aA){ar.click(function(){aA.setColor(l.get_random_color())})})(ap)}else{az.append($("<input />").attr("id",am).attr("name",am).val(ax))}}}}if(ai.help){az.append($("<div class='help'/>").text(ai.help))}}}ah(aj.get("params"),ac);var ad=this,ag=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ae=function(){ad.update_from_form($(Galaxy.modal.el));Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},af=function(ak){if((ak.keyCode||ak.which)===27){ag()}else{if((ak.keyCode||ak.which)===13){ae()}}};$(window).bind("keypress.check_enter_esc",af);Galaxy.modal.show({title:"Configure",body:ac,buttons:{Cancel:ag,Ok:ae}})},update_from_form:function(ac){var ad=this.model;var ae=false;ab.each(ad.get("params"),function(ah,af){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}ae=ad.set_param_value(ah.key,ag)||ae}})}});var c=function(ac,af,ag,ad,ae){this.track=ac;this.region=af;this.low=af.get("start");this.high=af.get("end");this.w_scale=ag;this.canvas=ad;this.html_elt=$("<div class='track-tile'/>").append(ad);this.data=ae;this.stale=false};c.prototype.predisplay_actions=function(){};var M=function(ac,af,ag,ad,ae){c.call(this,ac,af,ag,ad,ae)};M.prototype.predisplay_actions=function(){};var O=function(af,am,ao,ae,ah,ai,ap,ad,al){c.call(this,af,am,ao,ae,ah);this.mode=ai;this.all_slotted=ad;this.feature_mapper=al;this.has_icons=false;if(ap){this.has_icons=true;var aj=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:F,width:ae.width}).prependTo(this.html_elt);var ak=new y.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),an=ah.length,ag=$("<a/>").addClass("icon more-down").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a/>").addClass("icon more-across").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ag.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.DEEP_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()});ac.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.BROAD_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()})}};q(O.prototype,c.prototype);O.prototype.predisplay_actions=function(){var ad=this,ac={};if(ad.mode!=="Pack"){return}$(this.html_elt).hover(function(){this.hovered=true;$(this).mousemove()},function(){this.hovered=false;$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()}).mousemove(function(ao){if(!this.hovered){return}var aj=$(this).offset(),an=ao.pageX-aj.left,am=ao.pageY-aj.top,at=ad.feature_mapper.get_feature_data(an,am),ak=(at?at[0]:null);$(this).parents(".track-content").children(".overlay").children(".feature-popup").each(function(){if(!ak||$(this).attr("id")!==ak.toString()){$(this).remove()}});if(at){var af=ac[ak];if(!af){var ap={name:at[3],start:at[1],end:at[2],strand:at[4]},ai=ad.track.filters_manager.filters,ah;for(var al=0;al<ai.length;al++){ah=ai[al];ap[ah.name]=at[ah.index]}af=$("<div/>").attr("id",ak).addClass("feature-popup");var au=$("<table/>"),ar,aq,av;for(ar in ap){aq=ap[ar];av=$("<tr/>").appendTo(au);$("<th/>").appendTo(av).text(ar);$("<td/>").attr("align","left").appendTo(av).text(typeof(aq)==="number"?V(aq,2):aq)}af.append($("<div class='feature-popup-inner'>").append(au));ac[ak]=af}af.appendTo($(this).parents(".track-content").children(".overlay"));var ag=an+parseInt(ad.html_elt.css("left"),10)-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"),10)+7;af.css("left",ag+"px").css("top",ae+"px")}else{if(!ao.isPropagationStopped()){ao.stopPropagation();$(this).siblings().each(function(){$(this).trigger(ao)})}}}).mouseleave(function(){$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()})};var g=function(ad,ac,ae){q(ae,{drag_handle_class:"draghandle"});r.call(this,ad,ac,ae);this.dataset=null;if(ae.dataset){this.dataset=(ae.dataset instanceof Backbone.Model?ae.dataset:X.Dataset.findOrCreate(ae.dataset))}this.dataset_check_type="converted_datasets_state";this.data_url_extra_params={};this.data_query_wait=("data_query_wait" in ae?ae.data_query_wait:K);this.data_manager=("data_manager" in ae?ae.data_manager:new y.GenomeDataManager({dataset:this.dataset,genome:new y.Genome({key:ad.dbkey,chroms_info:{chrom_info:ad.chrom_data}}),data_mode_compatible:this.data_and_mode_compatible,can_subset:this.can_subset}));this.min_height_px=16;this.max_height_px=800;this.visible_height_px=this.prefs.height;this.content_div=$("<div class='track-content'>").appendTo(this.container_div);if(this.container){this.container.content_div.append(this.container_div);if(!("resize" in ae)||ae.resize){this.add_resize_handle()}}};q(g.prototype,r.prototype,{action_icons_def:[{name:"mode_icon",title:"Set display mode",css_class:"chevron-expand",on_click_fn:function(){}},r.prototype.action_icons_def[0],{name:"overview_icon",title:"Set as overview",css_class:"overview-icon",on_click_fn:function(ac){ac.view.set_overview(ac)}},r.prototype.action_icons_def[1],{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters()}else{ac.filters_manager.init_filters()}ac.filters_manager.toggle()}},{name:"tools_icon",title:"Tool",css_class:"hammer",on_click_fn:function(ac){ac.tool.toggle();if(ac.tool.is_visible()){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".tooltip").remove()}},{name:"param_space_viz_icon",title:"Tool parameter space visualization",css_class:"arrow-split",on_click_fn:function(ac){var af='<strong>Tool</strong>: <%= track.tool.name %><br/><strong>Dataset</strong>: <%= track.name %><br/><strong>Region(s)</strong>: <select name="regions"><option value="cur">current viewing area</option><option value="bookmarks">bookmarks</option><option value="both">current viewing area and bookmarks</option></select>',ae=ab.template(af,{track:ac});var ah=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new y.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new y.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}Galaxy.modal.hide();window.location.href=galaxy_config.root+"visualization/sweepster?"+$.param({dataset_id:ac.dataset.id,hda_ldda:ac.dataset.get("hda_ldda"),regions:JSON.stringify(new Backbone.Collection(al).toJSON())})},ag=function(ai){if((ai.keyCode||ai.which)===27){ah()}else{if((ai.keyCode||ai.which)===13){ad()}}};Galaxy.modal.show({title:"Visualize tool parameter space and output from different parameter settings?",body:ae,buttons:{No:ah,Yes:ad}})}},r.prototype.action_icons_def[2]],can_draw:function(){return this.dataset&&r.prototype.can_draw.call(this)},build_container_div:function(){return $("<div/>").addClass("track").attr("id","track_"+this.id).css("position","relative")},build_header_div:function(){var ac=$("<div class='track-header'/>");if(this.view.editor){this.drag_div=$("<div/>").addClass(this.drag_handle_class).appendTo(ac)}this.name_div=$("<div/>").addClass("track-name").appendTo(ac).text(this.prefs.name).attr("id",this.prefs.name.replace(/\s+/g,"-").replace(/[^a-zA-Z0-9\-]/g,"").toLowerCase());return ac},set_dataset:function(ac){this.dataset=ac;this.data_manager.set("dataset",ac)},on_resize:function(){this.request_draw({clear_tile_cache:true})},add_resize_handle:function(){var ac=this;var af=false;var ae=false;var ad=$("<div class='track-resize'>");$(ac.container_div).hover(function(){if(ac.prefs.content_visible){af=true;ad.show()}},function(){af=false;if(!ae){ad.hide()}});ad.hide().bind("dragstart",function(ag,ah){ae=true;ah.original_height=$(ac.content_div).height()}).bind("drag",function(ah,ai){var ag=Math.min(Math.max(ai.original_height+ai.deltaY,ac.min_height_px),ac.max_height_px);$(ac.tiles_div).css("height",ag);ac.visible_height_px=(ac.max_height_px===ag?0:ag);ac.on_resize()}).bind("dragend",function(ag,ah){ac.tile_cache.clear();ae=false;if(!af){ad.hide()}ac.config.get("values").height=ac.visible_height_px;ac.changed()}).appendTo(ac.container_div)},set_display_modes:function(af,ai){this.display_modes=af;this.mode=(ai?ai:(this.config&&this.config.get("values").mode?this.config.get("values").mode:this.display_modes[0]));this.action_icons.mode_icon.attr("title","Set display mode (now: "+this.mode+")");var ad=this,ag={};for(var ae=0,ac=ad.display_modes.length;ae<ac;ae++){var ah=ad.display_modes[ae];ag[ah]=function(aj){return function(){ad.change_mode(aj);ad.icons_div.show();ad.container_div.mouseleave(function(){ad.icons_div.hide()})}}(ah)}make_popupmenu(this.action_icons.mode_icon,ag)},build_action_icons:function(){r.prototype.build_action_icons.call(this,this.action_icons_def);if(this.display_modes!==undefined){this.set_display_modes(this.display_modes)}},hide_contents:function(){this.tiles_div.hide();this.container_div.find(".yaxislabel, .track-resize").hide()},show_contents:function(){this.tiles_div.show();this.container_div.find(".yaxislabel, .track-resize").show();this.request_draw()},get_type:function(){if(this instanceof W){return"LabelTrack"}else{if(this instanceof D){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof T){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof d){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.tiles_div.css("height","auto");ad.tiles_div.text("").children().remove();ad.container_div.removeClass("nodata error pending");if(!ad.dataset.id){return}var ac=$.Deferred(),af={hda_ldda:ad.dataset.get("hda_ldda"),data_type:this.dataset_check_type,chrom:ad.view.chrom,retry:ae};$.getJSON(this.dataset.url(),af,function(ag){if(!ag||ag==="error"||ag.kind==="error"){ad.container_div.addClass("error");ad.tiles_div.text(o);if(ag.message){ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("View error").click(function(){Galaxy.modal.show({title:"Trackster Error",body:"<pre>"+ag.message+"</pre>",buttons:{Close:function(){Galaxy.modal.hide()}}})}));ad.tiles_div.append($("<span/>").text(" "));ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("Try again").click(function(){ad.init(true)}))}}else{if(ag==="no converter"){ad.container_div.addClass("error");ad.tiles_div.text(J)}else{if(ag==="no data"||(ag.data!==undefined&&(ag.data===null||ag.data.length===0))){ad.container_div.addClass("nodata");ad.tiles_div.text(G)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(w);setTimeout(function(){ad.init()},ad.data_query_wait)}else{if(ag==="data"||ag.status==="data"){if(ag.valid_chroms){ad.valid_chroms=ag.valid_chroms;ad.update_icons()}ad.tiles_div.text(U);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when.apply($,ad.predraw_init()).done(function(){ac.resolve();ad.container_div.removeClass("nodata error pending");ad.request_draw()})}else{ac.resolve()}}}}}}});this.update_icons();return ac},predraw_init:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){ac.container_div.addClass("line-track");var af=ad.data;if(af&&af.min&&af.max){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.config.set_param_default_value("min_value",ae);ac.config.set_param_default_value("max_value",ag);ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},get_drawables:function(){return this}});var N=function(ae,ad,ag){g.call(this,ae,ad,ag);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in ag?ag.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=(ag.tool?new s(ab.extend(ag.tool,{track:this,tool_state:ag.tool_state})):null);this.tile_cache=new y.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){var af=new aa({model:this.tool});af.render();this.dynamic_tool_div=af.$el;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);if(!this.prefs.content_visible){this.tiles_div.hide()}this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(ag.mode){this.change_mode(ag.mode)}};q(N.prototype,r.prototype,g.prototype,{action_icons_def:g.prototype.action_icons_def.concat([{name:"show_more_rows_icon",title:"To minimize track height, not all feature rows are displayed. Click to display more rows.",css_class:"exclamation",on_click_fn:function(ac){$(".tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw({clear_tile_cache:true})},hide:true}]),copy:function(ac){var ad=this.to_dict();q(ad,{data_manager:this.data_manager});var ae=new this.constructor(this.view,ac,ad);ae.change_mode(this.mode);ae.enabled=this.enabled;return ae},set_filters_manager:function(ac){this.filters_manager=ac;this.header_div.after(this.filters_manager.parent_div)},to_dict:function(){return{track_type:this.get_type(),dataset:{id:this.dataset.id,hda_ldda:this.dataset.get("hda_ldda")},prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},set_min_max:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){var af=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.get("values").mode=ad;if(ad==="Auto"){this.data_manager.clear()}ac.request_draw({clear_tile_cache:true});this.action_icons.mode_icon.attr("title","Set display mode (now: "+ac.mode+")");return ac},update_icons:function(){var ac=this;if(ac.filters_available){ac.action_icons.filters_icon.show()}else{ac.action_icons.filters_icon.hide()}if(ac.tool){ac.action_icons.tools_icon.show();ac.action_icons.param_space_viz_icon.show()}else{ac.action_icons.tools_icon.hide();ac.action_icons.param_space_viz_icon.hide()}},_gen_tile_cache_key:function(ad,ac){return ad+"_"+ac},request_draw:function(ac){if(ac&&ac.clear_tile_cache){this.tile_cache.clear()}this.view.request_redraw(ac,this)},before_draw:function(){this.max_height_px=0},_draw:function(aq){if(!this.can_draw()){return}var an=aq&&aq.clear_after,al=this.view.low,ag=this.view.high,aj=ag-al,ad=this.view.container.width(),ap=this.view.resolution_px_b,af=1/ap;if(this.is_overview){al=this.view.max_low;ag=this.view.max_high;ap=ad/(view.max_high-view.max_low);af=1/ap}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(af*S)),ak,am,ah,ai=[],ao=[];while((ac*S*af)<ag){ak=Math.floor(ac*S*af);am=new y.GenomeRegion({chrom:this.view.chrom,start:ak,end:Math.min(ak+Math.ceil(S*af),this.view.max_high)});ah=this.draw_helper(am,ap,aq);ai.push(ah);$.when(ah).then(function(ar){ao.push(ar)});ac+=1}if(!an){this.tiles_div.children(".remove").removeClass("remove").remove()}var ae=this;$.when.apply($,ai).then(function(){ae.tiles_div.children(".remove").remove();ao=ab.filter(ao,function(ar){return ar!==null});if(ao.length!==0){ae.postdraw_actions(ao,ad,ap,an)}})},_add_yaxis_label:function(af,ah){var ad=this,ag=(af==="max"?"top":"bottom"),ai=(af==="max"?"max":"min"),ac=(af==="max"?"max_value":"min_value"),ae=this.container_div.find(".yaxislabel."+ag);ah=ah||function(){ad.request_draw({clear_tile_cache:true})};if(ae.length!==0){ae.text(ad.prefs[ac])}else{ae=$("<div/>").text(ad.prefs[ac]).make_text_editable({num_cols:12,on_finish:function(aj){$(".tooltip").remove();ad.config.set_param_value(ac,aj);ah()},help_text:"Set "+ai+" value"}).addClass("yaxislabel "+ag).css("color",this.prefs.label_color);this.container_div.prepend(ae)}},postdraw_actions:function(af,ag,ai,ac){var ae=ab.filter(af,function(aj){return(aj instanceof M)});if(ae.length>0){this.max_height_px=0;var ad=this;ab.each(af,function(aj){if(!(aj instanceof M)){aj.html_elt.remove();ad.draw_helper(aj.region,ai,{force:true,mode:"Coverage"})}});ad._add_yaxis_label("max")}else{this.container_div.find(".yaxislabel").remove();var ah=ab.find(af,function(aj){return aj.has_icons});if(ah){ab.each(af,function(aj){if(!aj.has_icons){aj.html_elt.css("padding-top",F)}})}}},get_mode:function(ac){return this.mode},update_auto_mode:function(ac){},_get_drawables:function(){return[this]},draw_helper:function(al,an,ao){if(!ao){ao={}}var ad=ao.force,ai=ao.mode||this.mode,af=1/an,ae=this,ag=this._get_drawables(),am=this._gen_tile_cache_key(an,al),ah=function(ap){return(ap&&"track" in ap)};var aj=(ad?undefined:ae.tile_cache.get_elt(am));if(aj){if(ah(aj)){ae.show_tile(aj,an)}return aj}if(ao.data_fetch===false){return null}var ak=function(){var ap=(ab.find(C,function(ar){return ar===ai})?"Coverage":ai);var aq=ab.map(ag,function(ar){return ar.data_manager.get_data(al,ap,af,ae.data_url_extra_params)});if(view.reference_track){aq.push(view.reference_track.data_manager.get_data(al,ai,af,view.reference_track.data_url_extra_params))}return aq};var ac=$.Deferred();ae.tile_cache.set_elt(am,ac);$.when.apply($,ak()).then(function(){var ap=ak(),av=ap,aB;if(view.reference_track){aB=view.reference_track.data_manager.subset_entry(ap.pop(),al)}var aw=[],at=[];ab.each(ag,function(aG,aD){var aF=aG.mode,aE=av[aD];if(aF==="Auto"){aF=aG.get_mode(aE);aG.update_auto_mode(aF)}aw.push(aF);at.push(aG.get_canvas_height(aE,aF,an,aq))});var au=ae.view.canvas_manager.new_canvas(),ax=al.get("start"),aC=al.get("end"),ar=0,aq=Math.ceil((aC-ax)*an)+ae.left_offset,az=ab.max(at),ay;au.width=aq;au.height=(ao.height||az);var aA=au.getContext("2d");aA.translate(ae.left_offset,0);if(ag.length>1){aA.globalAlpha=0.5;aA.globalCompositeOperation="source-over"}ab.each(ag,function(aE,aD){ay=aE.draw_tile(av[aD],aA,aw[aD],al,an,aB)});if(ay!==undefined){ae.tile_cache.set_elt(am,ay);ae.show_tile(ay,an)}ac.resolve(ay)});return ac},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_line_track_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.LinePainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new M(this,ag,ai,af,ac.data)},draw_tile:function(ac,ad,ag,af,ah,ae){},show_tile:function(ae,ah){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ah;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{this.tiles_div.append(ac)}this.max_height_px=Math.max(this.max_height_px,$(ae.canvas).height());ac.parent().children().css("height",this.max_height_px+"px");var af=this.max_height_px;if(this.visible_height_px!==0){af=Math.min(this.max_height_px,this.visible_height_px)}this.tiles_div.css("height",af+"px")},tool_region_and_parameters_str:function(af){var ac=this,ae=(af!==undefined?af.toString():"all"),ad=ab.values(ac.tool.get_inputs_dict()).join(", ");return" - region=["+ae+"], parameters=["+ad+"]"},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="bigwig"}else{if(ac.dataset_type==="bigwig"||ac.extra_info==="no_detail"){return false}else{return true}}}},can_subset:function(ac){if(ac.message||ac.extra_info==="no_detail"){return false}else{if(ac.dataset_type==="bigwig"){return(ac.data[1][0]-ac.data[0][0]===1)}}return true},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state"}});var W=function(ad,ac){var ae={resize:false};g.call(this,ad,ac,ae);this.container_div.addClass("label-track")};q(W.prototype,g.prototype,{build_header_div:function(){},init:function(){this.enabled=true},predraw_init:function(){},_draw:function(ag){var ae=this.view,af=ae.high-ae.low,aj=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/aj)*aj,ah=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ai=(ac-ae.low)/af*ah;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ai-1}));ac+=aj}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){N.call(this,ad,ac,ag);this.drawables=[];if("drawables" in ag){var af;for(var ae=0;ae<ag.drawables.length;ae++){af=ag.drawables[ae];this.drawables[ae]=p(af,ad,null);if(af.left_offset>this.left_offset){this.left_offset=af.left_offset}}this.enabled=true}ab.each(this.drawables,function(ah){if(ah instanceof d||ah instanceof T){ah.change_mode("Coverage")}});this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,N.prototype,{display_modes:C,action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_group()}}].concat(N.prototype.action_icons_def),to_dict:A.prototype.to_dict,add_drawable:A.prototype.add_drawable,unpack_drawables:A.prototype.unpack_drawables,change_mode:function(ac){N.prototype.change_mode.call(this,ac);for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].change_mode(ac)}},init:function(){var ae=[];for(var ad=0;ad<this.drawables.length;ad++){ae.push(this.drawables[ad].init())}var ac=this;$.when.apply($,ae).then(function(){ac.enabled=true;ac.request_draw()})},update_icons:function(){this.action_icons.filters_icon.hide();this.action_icons.tools_icon.hide();this.action_icons.param_space_viz_icon.hide()},can_draw:r.prototype.can_draw,_get_drawables:function(){return this.drawables},show_group:function(){var af=new P(this.view,this.container,{name:this.prefs.name}),ac;for(var ae=0;ae<this.drawables.length;ae++){ac=this.drawables[ae];ac.update_icons();af.add_drawable(ac);ac.container=af;af.content_div.append(ac.container_div)}var ad=this.container.replace_drawable(this,af,true);af.request_draw({clear_tile_cache:true})},before_draw:function(){N.prototype.before_draw.call(this);var ad=ab.min(ab.map(this.drawables,function(ae){return ae.prefs.min_value})),ac=ab.max(ab.map(this.drawables,function(ae){return ae.prefs.max_value}));this.prefs.min_value=ad;this.prefs.max_value=ac;ab.each(this.drawables,function(ae){ae.prefs.min_value=ad;ae.prefs.max_value=ac})},update_all_min_max:function(){var ac=this;ab.each(this.drawables,function(ad){ad.prefs.min_value=ac.prefs.min_value;ad.prefs.max_value=ac.prefs.max_value});this.request_draw({clear_tile_cache:true})},postdraw_actions:function(ai,ac,al,ah){N.prototype.postdraw_actions.call(this,ai,ac,al,ah);var ag=-1,ae;for(ae=0;ae<ai.length;ae++){var aj=ai[ae].html_elt.find("canvas").height();if(aj>ag){ag=aj}}for(ae=0;ae<ai.length;ae++){var af=ai[ae];if(af.html_elt.find("canvas").height()!==ag){this.draw_helper(af.region,al,{force:true,height:ag});af.html_elt.remove()}}var ad=this,ak=function(){ad.update_all_min_max()};this._add_yaxis_label("min",ak);this._add_yaxis_label("max",ak)}});var D=function(ac){N.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});this.left_offset=ac.canvas_manager.char_width_px;this.container_div.addClass("reference-track");this.data_url=galaxy_config.root+"api/genomes/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new y.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(D.prototype,r.prototype,N.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"height",type:"int",default_value:13,hidden:true}]),build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},predraw_init:function(){},can_draw:r.prototype.can_draw,draw_helper:function(ad,ae,ac){if(ae>this.view.canvas_manager.char_width_px){this.tiles_div.show();return N.prototype.draw_helper.call(this,ad,ae,ac)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(ae,ak,af,ah,al){var ad=this.data_manager.subset_entry(ae,ah),aj=ad.data;var ac=ak.canvas;ak.font=ak.canvas.manager.default_font;ak.textAlign="center";for(var ag=0,ai=aj.length;ag<ai;ag++){ak.fillStyle=this.view.get_base_color(aj[ag]);ak.fillText(aj[ag],Math.floor(ag*al),10)}return new c(this,ah,al,ac,ad)}});var h=function(ad,ac,ae){this.mode="Histogram";N.call(this,ad,ac,ae)};q(h.prototype,r.prototype,N.prototype,{display_modes:C,config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Color",type:"color",default_value:l.get_random_color()},{key:"min_value",label:"Min Value",type:"float",default_value:undefined},{key:"max_value",label:"Max Value",type:"float",default_value:undefined},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:30,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},before_draw:function(){},draw_tile:function(ac,ad,af,ae,ag){return this._draw_line_track_tile(ac,ad,af,ae,ag)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)},postdraw_actions:function(ad,ae,af,ac){this._add_yaxis_label("max");this._add_yaxis_label("min")}});var t=function(ad,ac,ae){this.mode="Heatmap";N.call(this,ad,ac,ae)};q(t.prototype,r.prototype,N.prototype,{display_modes:["Heatmap"],config_params:ab.union(r.prototype.config_params,[{key:"pos_color",label:"Positive Color",type:"color",default_value:"#FF8C00"},{key:"neg_color",label:"Negative Color",type:"color",default_value:"#4169E1"},{key:"min_value",label:"Min Value",type:"float",default_value:-1},{key:"max_value",label:"Max Value",type:"float",default_value:1},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:500,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new c(this,ag,ai,af,ac.data)}});var d=function(ad,ac,ae){N.call(this,ad,ac,ae);this.container_div.addClass("feature-track");this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(d.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true,help:"Show the number of items in each bin when drawing summary histogram"},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"connector_style",label:"Connector style",type:"select",default_value:"fishbones",options:[{label:"Line with arrows",value:"fishbone"},{label:"Arcs",value:"arcs"}]},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.set_painter_from_config();this.request_draw({clear_tile_cache:true})},set_painter_from_config:function(){if(this.config.get("values").connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},postdraw_actions:function(am,ae,an,al){N.prototype.postdraw_actions.call(this,am,ae,an,al);var ag=this,ah;if(ag.filters_manager){var af=ag.filters_manager.filters,aj;for(aj=0;aj<af.length;aj++){af[aj].update_ui_elt()}var ai=false,ak,ad;for(ah=0;ah<am.length;ah++){if(am[ah].data.length){ak=am[ah].data[0];for(aj=0;aj<af.length;aj++){ad=af[aj];if(ad.applies_to(ak)&&ad.min!==ad.max){ai=true;break}}}}if(ag.filters_available!==ai){ag.filters_available=ai;if(!ag.filters_available){ag.filters_manager.hide()}ag.update_icons()}}if(am[0] instanceof O){var ac=true;for(ah=0;ah<am.length;ah++){if(!am[ah].all_slotted){ac=false;break}}if(!ac){this.action_icons.show_more_rows_icon.show()}else{this.action_icons.show_more_rows_icon.hide()}}else{this.action_icons.show_more_rows_icon.hide()}},update_auto_mode:function(ac){if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}this.action_icons.mode_icon.attr("title","Set display mode (now: Auto/"+ac+")")}},incremental_slots:function(ag,ac,af){var ad=this.view.canvas_manager.dummy_context,ae=this.slotters[ag];if(!ae||(ae.mode!==af)){ae=new (u.FeatureSlotter)(ag,af,B,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.extra_info==="no_detail"||this.is_overview){mode="no_detail"}else{if(this.view.high-this.view.low>I){mode="Squish"}else{mode="Pack"}}return mode},get_canvas_height:function(ac,ag,ah,ad){if(ag==="Coverage"||ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var af=this.incremental_slots(ah,ac.data,ag);var ae=new (this.painter)(null,null,null,this.prefs,ag);return Math.max(this.min_height_px,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,af,aj,ae){var ap=this,ad=aq.canvas,ax=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(am.dataset_type==="bigwig"){return this._draw_line_track_tile(am,aq,ao,af,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var ar=0,au=am.data.length;ar<au;ar++){var ah=am.data[ar];var at=false;var al;for(var aw=0,aB=ak.length;aw<aB;aw++){al=ak[aw];al.update_attrs(ah);if(!al.keep(ah)){at=true;break}}if(!at){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aA=(this.filters_manager.alpha_filter?new E(this.filters_manager.alpha_filter):null),ay=(this.filters_manager.height_filter?new E(this.filters_manager.height_filter):null),az=new (this.painter)(ai,ax,ac,this.prefs,ao,aA,ay,ae,function(aC){return ap.view.get_base_color(aC)});var av=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){av=az.draw(aq,ad.width,ad.height,aj,an);av.translation=-ag}return new O(ap,af,aj,ad,am.data,ao,am.message,all_slotted,av)}});var Z=function(ad,ac,ae){N.call(this,ad,ac,ae);this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Histogram color",type:"color",default_value:l.get_random_color()},{key:"show_sample_data",label:"Show sample data",type:"bool",default_value:true},{key:"show_labels",label:"Show summary and sample labels",type:"bool",default_value:true},{key:"summary_height",label:"Locus summary height",type:"float",default_value:20},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,af,ah,ag,ai){if(ac.dataset_type==="bigwig"){return this._draw_line_track_tile(ac,af,"Histogram",ag,ai)}else{var ae=this.view,ad=new (this.painter)(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah,function(aj){return ae.get_base_color(aj)});ad.draw(af,af.canvas.width,af.canvas.height,ai);return new c(this,ag,ai,af.canvas,ac.data)}},get_canvas_height:function(ac,ag,ah,ae){if(ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var ad=(this.dataset.get_metadata("sample_names")?this.dataset.get_metadata("sample_names").length:0);if(ad===0&&ac.data.length!==0){ad=ac.data[0][7].match(/,/g);if(ad===null){ad=1}else{ad=ad.length+1}}var af=new (this.painter)(null,null,null,this.prefs,ag);return af.get_required_height(ad)}},predraw_init:function(){var ac=[g.prototype.predraw_init.call(this)];if(!this.dataset.get_metadata("sample_names")){ac.push(this.dataset.fetch())}return ac},postdraw_actions:function(ag,ah,aj,ad){N.prototype.postdraw_actions.call(this,ag,ah,aj,ad);var af=ab.filter(ag,function(ak){return(ak instanceof M)});var ae=this.dataset.get_metadata("sample_names");if(af.length===0&&this.prefs.show_labels&&ae){var ac;if(this.container_div.find(".yaxislabel.variant").length===0){ac=this.prefs.summary_height/2;this.tiles_div.prepend($("<div/>").text("Summary").addClass("yaxislabel variant top").css({"font-size":ac+"px",top:(this.prefs.summary_height-ac)/2+"px"}));if(this.prefs.show_sample_data){var ai=ae.join("<br/>");this.tiles_div.prepend($("<div/>").html(ai).addClass("yaxislabel variant top sample").css({top:this.prefs.summary_height+2,}))}}ac=(this.mode==="Squish"?5:10)+"px";$(this.tiles_div).find(".sample").css({"font-size":ac,"line-height":ac});$(this.tiles_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel.variant").remove()}}});var T=function(ad,ac,ae){d.call(this,ad,ac,ae);this.painter=(ad.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(T.prototype,r.prototype,N.prototype,d.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block and sense strand color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_insertions",label:"Show insertions",type:"bool",default_value:false},{key:"show_differences",label:"Show differences only",type:"bool",default_value:true},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})}});var e={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:d,LineTrack:h,ReadTrack:T,VariantTrack:Z,VcfTrack:Z};var p=function(ae,ad,ac){if("copy" in ae){return ae.copy(ac)}else{var af=ae.obj_type;if(!af){af=ae.track_type}return new e[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:d,DiagonalHeatmapTrack:t,ReadTrack:T,VariantTrack:Z,CompositeTrack:f,object_from_template:p}});
\ No newline at end of file
+define(["libs/underscore","viz/visualization","viz/trackster/util","viz/trackster/slotting","viz/trackster/painters","viz/trackster/filters","mvc/data","mvc/tools"],function(ab,y,l,u,L,i,X,R){var q=ab.extend;var n={};var k=function(ac,ad){n[ac.attr("id")]=ad};var m=function(ac,ae,ag,af){ag=".group";var ad={};n[ac.attr("id")]=af;ac.bind("drag",{handle:"."+ae,relative:true},function(ao,ap){var an=$(this),at=$(this).parent(),ak=at.children(),am=n[$(this).attr("id")],aj,ai,aq,ah,al;ai=$(this).parents(ag);if(ai.length!==0){aq=ai.position().top;ah=aq+ai.outerHeight();var ar=n[ai.attr("id")];if(ap.offsetY<aq){$(this).insertBefore(ai);ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);ar.remove_drawable(am);ar.container.add_drawable(am);return}}}ai=null;for(al=0;al<ak.length;al++){aj=$(ak.get(al));aq=aj.position().top;ah=aq+aj.outerHeight();if(aj.is(ag)&&this!==aj.get(0)&&ap.offsetY>=aq&&ap.offsetY<=ah){if(ap.offsetY-aq<ah-ap.offsetY){aj.find(".content-div").prepend(this)}else{aj.find(".content-div").append(this)}if(am.container){am.container.remove_drawable(am)}n[aj.attr("id")].add_drawable(am);return}}for(al=0;al<ak.length;al++){aj=$(ak.get(al));if(ap.offsetY<aj.position().top&&!(aj.hasClass("reference-track")||aj.hasClass("intro"))){break}}if(al===ak.length){if(this!==ak.get(al-1)){at.append(this);n[at.attr("id")].move_drawable(am,al)}}else{if(this!==ak.get(al)){$(this).insertBefore(ak.get(al));n[at.attr("id")].move_drawable(am,(ap.deltaY>0?al-1:al))}}}).bind("dragstart",function(){ad["border-top"]=ac.css("border-top");ad["border-bottom"]=ac.css("border-bottom");$(this).css({"border-top":"1px solid blue","border-bottom":"1px solid blue"})}).bind("dragend",function(){$(this).css(ad)})};var F=20,B=100,I=12000,S=400,K=5000,x=100,o="Cannot display dataset due to an error. ",J="A converter for this dataset is not installed. Please check your datatypes_conf.xml file.",G="No data for this chrom/contig.",w="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",z="Tool cannot be rerun: ",b="Loading data...",U="Ready for display",Q=10,H=20,C=["Histogram","Line","Filled","Intensity"];function V(ad,ac){if(!ac){ac=0}var ae=Math.pow(10,ac);return Math.round(ad*ae)/ae}var r=function(ad,ac,af){if(!r.id_counter){r.id_counter=0}this.id=r.id_counter++;this.view=ad;this.container=ac;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.config=new j({params:this.config_params,onchange:this.config_onchange,saved_values:af.prefs});this.prefs=this.config.get("values");if(!this.prefs.name){this.prefs.name=af.name}if(this.config_onchange){this.config.on("change:values",this.config_onchange,this)}this.container_div=this.build_container_div();this.header_div=this.build_header_div();if(this.header_div){this.container_div.append(this.header_div);this.icons_div=$("<div/>").css("float","left").hide().appendTo(this.header_div);this.build_action_icons(this.action_icons_def);this.header_div.append($("<div style='clear: both'/>"));this.header_div.dblclick(function(ag){ag.stopPropagation()});var ae=this;this.container_div.hover(function(){ae.icons_div.show()},function(){ae.icons_div.hide()});$("<div style='clear: both'/>").appendTo(this.container_div)}};r.prototype.action_icons_def=[{name:"toggle_icon",title:"Hide/show content",css_class:"toggle",on_click_fn:function(ac){if(ac.prefs.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.prefs.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.prefs.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var ac=new a({model:ad.config});ac.render()}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".tooltip").remove();ac.remove()}}];q(r.prototype,{config_params:[{key:"name",label:"Name",type:"text",default_value:""},{key:"content_visible",type:"bool",default_value:true,hidden:true}],config_onchange:function(){this.track.set_name(this.track.config.get("values").name)},init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.prefs.content_visible){return true}return false},request_draw:function(){},_draw:function(ac){},to_dict:function(){},set_name:function(ac){this.old_name=this.prefs.name;this.prefs.name=ac;this.name_div.text(this.prefs.name)},revert_name:function(){if(this.old_name){this.prefs.name=this.old_name;this.name_div.text(this.prefs.name)}},remove:function(){this.changed();this.container.remove_drawable(this);var ac=this.view;this.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})},build_container_div:function(){},build_header_div:function(){},add_action_icon:function(ad,ai,ah,ag,ac,af){var ae=this;this.action_icons[ad]=$("<a/>").attr("title",ai).addClass("icon-button").addClass(ah).tooltip().click(function(){ag(ae)}).appendTo(this.icons_div);if(af){this.action_icons[ad].hide()}},build_action_icons:function(ac){var ae;for(var ad=0;ad<ac.length;ad++){ae=ac[ad];this.add_action_icon(ae.name,ae.title,ae.css_class,ae.on_click_fn,ae.prepend,ae.hide)}},update_icons:function(){},hide_contents:function(){},show_contents:function(){},get_drawables:function(){}});var A=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(A.prototype,r.prototype,{unpack_drawables:function(ae){this.drawables=[];var ad;for(var ac=0;ac<ae.length;ac++){ad=p(ae[ac],this.view,this);this.add_drawable(ad)}},init:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].init()}},_draw:function(ac){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad]._draw(ac)}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{prefs:this.prefs,obj_type:this.obj_type,drawables:ad}},add_drawable:function(ac){this.drawables.push(ac);ac.container=this;this.changed()},add_drawable_before:function(ae,ac){this.changed();var ad=this.drawables.indexOf(ac);if(ad!==-1){this.drawables.splice(ad,0,ae);return true}return false},replace_drawable:function(ae,ac,ad){var af=this.drawables.indexOf(ae);if(af!==-1){this.drawables[af]=ac;if(ad){ae.container_div.replaceWith(ac.container_div)}this.changed()}return af},remove_drawable:function(ad){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);ad.container=null;this.changed();return true}return false},move_drawable:function(ad,ae){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);this.drawables.splice(ae,0,ad);this.changed();return true}return false},get_drawables:function(){return this.drawables},get_tracks:function(af){var ac=this.drawables.slice(0),ad=[],ae;while(ac.length!==0){ae=ac.shift();if(ae instanceof af){ad.push(ae)}else{if(ae.drawables){ac=ac.concat(ae.drawables)}}}return ad}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});A.call(this,ad,ac,af);this.content_div=$("<div/>").addClass("content-div").attr("id","group_"+this.id+"_content_div").appendTo(this.container_div);k(this.container_div,this);k(this.content_div,this);m(this.container_div,this.drag_handle_class,".group",this);this.filters_manager=new i.FiltersManager(this);this.header_div.after(this.filters_manager.parent_div);this.saved_filters_managers=[];if("drawables" in af){this.unpack_drawables(af.drawables)}if("filters" in af){var ae=this.filters_manager;this.filters_manager=new i.FiltersManager(this,af.filters);ae.parent_div.replaceWith(this.filters_manager.parent_div);if(af.filters.visible){this.setup_multitrack_filtering()}}};q(P.prototype,r.prototype,A.prototype,{action_icons_def:[r.prototype.action_icons_def[0],r.prototype.action_icons_def[1],{name:"composite_icon",title:"Show composite track",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_composite_track()}},{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters();ac._restore_filter_managers()}else{ac.setup_multitrack_filtering();ac.request_draw({clear_tile_cache:true})}ac.filters_manager.toggle()}},r.prototype.action_icons_def[2]],build_container_div:function(){var ac=$("<div/>").addClass("group").attr("id","group_"+this.id);if(this.container){this.container.content_div.append(ac)}return ac},build_header_div:function(){var ac=$("<div/>").addClass("track-header");ac.append($("<div/>").addClass(this.drag_handle_class));this.name_div=$("<div/>").addClass("track-name").text(this.prefs.name).appendTo(ac);return ac},hide_contents:function(){this.tiles_div.hide()},show_contents:function(){this.tiles_div.show();this.request_draw()},update_icons:function(){var ae=this.drawables.length;if(ae===0){this.action_icons.composite_icon.hide();this.action_icons.filters_icon.hide()}else{if(ae===1){if(this.drawables[0] instanceof f){this.action_icons.composite_icon.show()}this.action_icons.filters_icon.hide()}else{var al,ak,ai,ao=true,ag=this.drawables[0].get_type(),ac=0;for(al=0;al<ae;al++){ai=this.drawables[al];if(ai.get_type()!==ag){can_composite=false;break}if(ai instanceof d){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".tooltip").remove()}if(ac>1&&ac===this.drawables.length){var ap={},ad;ai=this.drawables[0];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];ap[ad.name]=[ad]}for(al=1;al<this.drawables.length;al++){ai=this.drawables[al];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];if(ad.name in ap){ap[ad.name].push(ad)}}}this.filters_manager.remove_all();var af,ah,aj,am;for(var an in ap){af=ap[an];if(af.length===ac){ah=new i.NumberFilter({name:af[0].name,index:af[0].index});this.filters_manager.add_filter(ah)}}if(this.filters_manager.filters.length>0){this.action_icons.filters_icon.show()}else{this.action_icons.filters_icon.hide()}}else{this.action_icons.filters_icon.hide()}}}},_restore_filter_managers:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].filters_manager=this.saved_filters_managers[ac]}this.saved_filters_managers=[]},setup_multitrack_filtering:function(){if(this.filters_manager.filters.length>0){this.saved_filters_managers=[];for(var ac=0;ac<this.drawables.length;ac++){drawable=this.drawables[ac];this.saved_filters_managers.push(drawable.filters_manager);drawable.filters_manager=this.filters_manager}}this.filters_manager.init_filters()},show_composite_track:function(){var ad=new f(this.view,this.view,{name:this.prefs.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ad,true);ad.request_draw()},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){A.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(A.prototype.to_dict.call(this),{filters:this.filters_manager.to_dict()});if(this.filters_manager.visible()){this.setup_multitrack_filtering()}return ac},request_draw:function(ac){ab.each(this.drawables,function(ad){ad.request_draw(ac)})}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});A.call(this,"View",ac.container,ac);this.chrom=null;this.vis_id=ac.vis_id;this.dbkey=ac.dbkey;this.label_tracks=[];this.tracks_to_be_redrawn=[];this.max_low=0;this.max_high=0;this.zoom_factor=3;this.min_separation=30;this.has_changes=false;this.load_chroms_deferred=null;this.render();this.canvas_manager=new y.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new j({track:this,params:[{key:"a_color",label:"A Color",type:"color",default_value:"#FF0000"},{key:"c_color",label:"C Color",type:"color",default_value:"#00FF00"},{key:"g_color",label:"G Color",type:"color",default_value:"#0000FF"},{key:"t_color",label:"T Color",type:"color",default_value:"#FF00FF"},{key:"n_color",label:"N Color",type:"color",default_value:"#AAAAAA"}],saved_values:ac.prefs,onchange:function(){track.request_redraw({clear_tile_cache:true})}})},render:function(){this.requested_redraw=false;var ae=this.container,ac=this;this.top_container=$("<div/>").addClass("top-container").appendTo(ae);this.browser_content_div=$("<div/>").addClass("content").css("position","relative").appendTo(ae);this.bottom_container=$("<div/>").addClass("bottom-container").appendTo(ae);this.top_labeltrack=$("<div/>").addClass("top-labeltrack").appendTo(this.top_container);this.viewport_container=$("<div/>").addClass("viewport-container").attr("id","viewport-container").appendTo(this.browser_content_div);this.content_div=this.viewport_container;k(this.viewport_container,ac);this.intro_div=$("<div/>").addClass("intro").appendTo(this.viewport_container).hide();var af=$("<div/>").text("Add Datasets to Visualization").addClass("action-button").appendTo(this.intro_div).click(function(){y.select_datasets(galaxy_config.root+"visualization/list_current_history_datasets",galaxy_config.root+"api/datasets",{"f-dbkey":ac.dbkey},function(ag){ab.each(ag,function(ah){ac.add_drawable(p(ah,ac,ac))})})});this.nav_labeltrack=$("<div/>").addClass("nav-labeltrack").appendTo(this.bottom_container);this.nav_container=$("<div/>").addClass("trackster-nav-container").prependTo(this.top_container);this.nav=$("<div/>").addClass("trackster-nav").appendTo(this.nav_container);this.overview=$("<div/>").addClass("overview").appendTo(this.bottom_container);this.overview_viewport=$("<div/>").addClass("overview-viewport").appendTo(this.overview);this.overview_close=$("<a/>").attr("title","Close overview").addClass("icon-button overview-close tooltip").hide().appendTo(this.overview_viewport);this.overview_highlight=$("<div/>").addClass("overview-highlight").hide().appendTo(this.overview_viewport);this.overview_box_background=$("<div/>").addClass("overview-boxback").appendTo(this.overview_viewport);this.overview_box=$("<div/>").addClass("overview-box").appendTo(this.overview_viewport);this.default_overview_height=this.overview_box.height();this.nav_controls=$("<div/>").addClass("nav-controls").appendTo(this.nav);this.chrom_select=$("<select/>").attr({name:"chrom"}).css("width","15em").append("<option value=''>Loading</option>").appendTo(this.nav_controls);var ad=function(ag){if(ag.type==="focusout"||(ag.keyCode||ag.which)===13||(ag.keyCode||ag.which)===27){if((ag.keyCode||ag.which)!==27){ac.go_to($(this).val())}$(this).hide();$(this).val("");ac.location_span.show();ac.chrom_select.show()}};this.nav_input=$("<input/>").addClass("nav-input").hide().bind("keyup focusout",ad).appendTo(this.nav_controls);this.location_span=$("<span/>").addClass("location").attr("original-title","Click to change location").tooltip({placement:"bottom"}).appendTo(this.nav_controls);this.location_span.click(function(){ac.location_span.hide();ac.chrom_select.hide();ac.nav_input.val(ac.chrom+":"+ac.low+"-"+ac.high);ac.nav_input.css("display","inline-block");ac.nav_input.select();ac.nav_input.focus();ac.nav_input.autocomplete({source:function(ai,ag){var aj=[],ah=$.map(ac.get_tracks(d),function(ak){return ak.data_manager.search_features(ai.term).success(function(al){aj=aj.concat(al)})});$.when.apply($,ah).done(function(){ag($.map(aj,function(ak){return{label:ak[0],value:ak[1]}}))})}})});if(this.vis_id!==undefined){this.hidden_input=$("<input/>").attr("type","hidden").val(this.vis_id).appendTo(this.nav_controls)}this.zo_link=$("<a/>").attr("id","zoom-out").attr("title","Zoom out").tooltip({placement:"bottom"}).click(function(){ac.zoom_out();ac.request_redraw()}).appendTo(this.nav_controls);this.zi_link=$("<a/>").attr("id","zoom-in").attr("title","Zoom in").tooltip({placement:"bottom"}).click(function(){ac.zoom_in();ac.request_redraw()}).appendTo(this.nav_controls);this.load_chroms_deferred=this.load_chroms({low:0});this.chrom_select.bind("change",function(){ac.change_chrom(ac.chrom_select.val())});this.browser_content_div.click(function(ag){$(this).find("input").trigger("blur")});this.browser_content_div.bind("dblclick",function(ag){ac.zoom_in(ag.pageX,this.viewport_container)});this.overview_box.bind("dragstart",function(ag,ah){this.current_x=ah.offsetX}).bind("drag",function(ag,ai){var aj=ai.offsetX-this.current_x;this.current_x=ai.offsetX;var ah=Math.round(aj/ac.viewport_container.width()*(ac.max_high-ac.max_low));ac.move_delta(-ah)});this.overview_close.click(function(){ac.reset_overview()});this.viewport_container.bind("draginit",function(ag,ah){if(ag.clientX>ac.viewport_container.width()-16){return false}}).bind("dragstart",function(ag,ah){ah.original_low=ac.low;ah.current_height=ag.clientY;ah.current_x=ah.offsetX}).bind("drag",function(ai,ak){var ag=$(this);var al=ak.offsetX-ak.current_x;var ah=ag.scrollTop()-(ai.clientY-ak.current_height);ag.scrollTop(ah);ak.current_height=ai.clientY;ak.current_x=ak.offsetX;var aj=Math.round(al/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}).bind("mousewheel",function(ai,ak,ah,ag){if(ah){ah*=50;var aj=Math.round(-ah/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}});this.top_labeltrack.bind("dragstart",function(ag,ah){return $("<div />").css({height:ac.browser_content_div.height()+ac.top_labeltrack.height()+ac.nav_labeltrack.height()+1,top:"0px",position:"absolute","background-color":"#ccf",opacity:0.5,"z-index":1000}).appendTo($(this))}).bind("drag",function(ak,al){$(al.proxy).css({left:Math.min(ak.pageX,al.startX)-ac.container.offset().left,width:Math.abs(ak.pageX-al.startX)});var ah=Math.min(ak.pageX,al.startX)-ac.container.offset().left,ag=Math.max(ak.pageX,al.startX)-ac.container.offset().left,aj=(ac.high-ac.low),ai=ac.viewport_container.width();ac.update_location(Math.round(ah/ai*aj)+ac.low,Math.round(ag/ai*aj)+ac.low)}).bind("dragend",function(al,am){var ah=Math.min(al.pageX,am.startX),ag=Math.max(al.pageX,am.startX),aj=(ac.high-ac.low),ai=ac.viewport_container.width(),ak=ac.low;ac.low=Math.round(ah/ai*aj)+ak;ac.high=Math.round(ag/ai*aj)+ak;$(am.proxy).remove();ac.request_redraw()});this.add_label_track(new W(this,{content_div:this.top_labeltrack}));this.add_label_track(new W(this,{content_div:this.nav_labeltrack}));$(window).bind("resize",function(){if(this.resize_timer){clearTimeout(this.resize_timer)}this.resize_timer=setTimeout(function(){ac.resize_window()},500)});$(document).bind("redraw",function(){ac.redraw()});this.reset();$(window).trigger("resize")},get_base_color:function(ac){return this.config.get("values")[ac.toLowerCase()+"_color"]||this.config.get("values").n_color}});q(Y.prototype,A.prototype,{changed:function(){this.has_changes=true},update_intro_div:function(){if(this.drawables.length===0){this.intro_div.show()}else{this.intro_div.hide()}},trigger_navigate:function(ad,af,ac,ag){if(this.timer){clearTimeout(this.timer)}if(ag){var ae=this;this.timer=setTimeout(function(){ae.trigger("navigate",ad+":"+af+"-"+ac)},500)}else{view.trigger("navigate",ad+":"+af+"-"+ac)}},update_location:function(ac,ae){this.location_span.text(commatize(ac)+" - "+commatize(ae));this.nav_input.val(this.chrom+":"+commatize(ac)+"-"+commatize(ae));var ad=view.chrom_select.val();if(ad!==""){this.trigger_navigate(ad,view.low,view.high,true)}},load_chroms:function(ae){ae.num=x;var ac=this,ad=$.Deferred();$.ajax({url:galaxy_config.root+"api/genomes/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){var ah=new D(ac);ac.add_label_track(ah);ac.reference_track=ah}ac.chrom_data=ag.chrom_info;var ak='<option value="">Select Chrom/Contig</option>';for(var aj=0,af=ac.chrom_data.length;aj<af;aj++){var ai=ac.chrom_data[aj].chrom;ak+='<option value="'+ai+'">'+ai+"</option>"}if(ag.prev_chroms){ak+='<option value="previous">Previous '+x+"</option>"}if(ag.next_chroms){ak+='<option value="next">Next '+x+"</option>"}ac.chrom_select.html(ak);ac.chrom_start_index=ag.start_index;ad.resolve(ag.chrom_info)},error:function(){alert("Could not load chroms for this dbkey:",ac.dbkey)}});return ad},change_chrom:function(ah,ad,aj){var ae=this;if(!ae.chrom_data){ae.load_chroms_deferred.then(function(){ae.change_chrom(ah,ad,aj)});return}if(!ah||ah==="None"){return}if(ah==="previous"){ae.load_chroms({low:this.chrom_start_index-x});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+x});return}var ai=$.grep(ae.chrom_data,function(ak,al){return ak.chrom===ah})[0];if(ai===undefined){ae.load_chroms({chrom:ah},function(){ae.change_chrom(ah,ad,aj)});return}else{if(ah!==ae.chrom){ae.chrom=ah;ae.chrom_select.val(ae.chrom);ae.max_high=ai.len-1;ae.reset();for(var ag=0,ac=ae.drawables.length;ag<ac;ag++){var af=ae.drawables[ag];if(af.init){af.init()}}if(ae.reference_track){ae.reference_track.init()}}if(ad&&aj){ae.low=Math.max(ad,0);ae.high=Math.min(aj,ae.max_high)}else{ae.low=0;ae.high=ae.max_high}ae.reset_overview();ae.request_redraw()}},go_to:function(ag){ag=ag.replace(/,/g,"");ag=ag.replace(/:|\-/g," ");var ad=ag.split(/\s+/),af=ad[0],ae=(ad[1]?parseInt(ad[1],10):null),ac=(ad[2]?parseInt(ad[2],10):null);if(!ac){ae=ae-15;ac=ae+15}this.change_chrom(af,ae,ac)},move_fraction:function(ae){var ac=this;var ad=ac.high-ac.low;this.move_delta(ae*ad)},move_delta:function(af){var ac=this;var ae=ac.high-ac.low;if(ac.low-af<ac.max_low){ac.low=ac.max_low;ac.high=ac.max_low+ae}else{if(ac.high-af>ac.max_high){ac.high=ac.max_high;ac.low=ac.max_high-ae}else{ac.high-=af;ac.low-=af}}ac.request_redraw({data_fetch:false});if(this.redraw_on_move_fn){clearTimeout(this.redraw_on_move_fn)}this.redraw_on_move_fn=setTimeout(function(){ac.request_redraw()},200);var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);ac.init();this.changed();this.update_intro_div()},add_label_track:function(ac){ac.view=this;ac.init();this.label_tracks.push(ac)},remove_drawable:function(ae,ad){A.prototype.remove_drawable.call(this,ae);if(ad){var ac=this;ae.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})}},reset:function(){this.low=this.max_low;this.high=this.max_high;this.viewport_container.find(".yaxislabel").remove()},request_redraw:function(ad,ae){var ac=this,af=(ae?[ae]:ac.drawables);ab.each(af,function(ag){var ah=ab.find(ac.tracks_to_be_redrawn,function(ai){return ai[0]===ag});if(ah){ah[1]=ad}else{ac.tracks_to_be_redrawn.push([ag,ad])}});if(!this.requested_redraw){requestAnimationFrame(function(){ac._redraw()});this.requested_redraw=true}},_redraw:function(){this.requested_redraw=false;var ac=this.low,ag=this.high;if(ac<this.max_low){ac=this.max_low}if(ag>this.max_high){ag=this.max_high}var ad=this.high-this.low;if(this.high!==0&&ad<this.min_separation){ag=ac+this.min_separation}this.low=Math.floor(ac);this.high=Math.ceil(ag);this.update_location(this.low,this.high);this.resolution_px_b=this.viewport_container.width()/(this.high-this.low);var af=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ah=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ae=13;this.overview_box.css({left:af,width:Math.max(ae,ah)}).show();if(ah<ae){this.overview_box.css("left",af-(ae-ah)/2)}if(this.overview_highlight){this.overview_highlight.css({left:af,width:ah})}ab.each(this.tracks_to_be_redrawn,function(ak){var ai=ak[0],aj=ak[1];if(ai){ai._draw(aj)}});this.tracks_to_be_redrawn=[];ab.each(this.label_tracks,function(ai){ai._draw()})},zoom_in:function(ad,ae){if(this.max_high===0||this.high-this.low<=this.min_separation){return}var af=this.high-this.low,ag=af/2+this.low,ac=(af/this.zoom_factor)/2;if(ad){ag=ad/this.viewport_container.width()*(this.high-this.low)+this.low}this.low=Math.round(ag-ac);this.high=Math.round(ag+ac);this.changed();this.request_redraw()},zoom_out:function(){if(this.max_high===0){return}var ad=this.high-this.low,ae=ad/2+this.low,ac=(ad*this.zoom_factor)/2;this.low=Math.round(ae-ac);this.high=Math.round(ae+ac);this.changed();this.request_redraw()},resize_window:function(){this.viewport_container.height(this.container.height()-this.top_container.height()-this.bottom_container.height());this.request_redraw()},set_overview:function(ae){if(this.overview_drawable){if(this.overview_drawable.dataset.id===ae.dataset.id){return}this.overview_viewport.find(".track").remove()}var ad=ae.copy({content_div:this.overview_viewport}),ac=this;ad.header_div.hide();ad.is_overview=true;ac.overview_drawable=ad;this.overview_drawable.postdraw_actions=function(){ac.overview_highlight.show().height(ac.overview_drawable.content_div.height());ac.overview_viewport.height(ac.overview_drawable.content_div.height()+ac.overview_box.outerHeight());ac.overview_close.show();ac.resize_window()};ac.overview_drawable.request_draw();this.changed()},reset_overview:function(){$(".tooltip").remove();this.overview_viewport.find(".track-tile").remove();this.overview_viewport.height(this.default_overview_height);this.overview_box.height(this.default_overview_height);this.overview_close.hide();this.overview_highlight.hide();view.resize_window();view.overview_drawable=null}});var s=R.Tool.extend({defaults:{track:null},initialize:function(ac){if(ac.tool_state!==undefined){this.set("hidden",ac.tool_state.hidden)}this.remove_inputs(["data","hidden_data","conditional"])},state_dict:function(ac){return ab.extend(this.get_inputs_dict(),{hidden:!this.is_visible()})}});var v=Backbone.View.extend({events:{"change input":"update_value"},render:function(){var ae=this.$el.addClass("param-row"),af=this.model;var ac=$("<div>").addClass("param-label").text(af.get("label")).appendTo(ae);var ad=$("<div/>").addClass("param-input").html(af.get("html")).appendTo(ae);ad.find(":input").val(af.get("value"));$("<div style='clear: both;'/>").appendTo(ae)},update_value:function(ac){this.model.set_value($(ac.target).val())}});var aa=Backbone.View.extend({initialize:function(ac){this.model.on("change:hidden",this.set_visible,this)},render:function(){var ad=this;tool=this.model,parent_div=this.$el.addClass("dynamic-tool").hide();parent_div.bind("drag",function(ah){ah.stopPropagation()}).click(function(ah){ah.stopPropagation()}).bind("dblclick",function(ah){ah.stopPropagation()}).keydown(function(ah){ah.stopPropagation()});var ae=$("<div class='tool-name'>").appendTo(parent_div).text(tool.get("name"));tool.get("inputs").each(function(ai){var ah=new v({model:ai});ah.render();parent_div.append(ah.$el)});parent_div.find("input").click(function(){$(this).select()});var af=$("<div>").addClass("param-row").appendTo(parent_div);var ag=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(af);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(af);ac.click(function(){ad.run_on_region()});ag.click(function(){ad.run_on_dataset()});if(tool.is_visible()){this.$el.show()}},set_visible:function(){if(this.model.is_visible()){this.$el.show()}else{this.$el.hide()}},update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},run_on_dataset:function(){var ac=this.model;this.run({target_dataset_id:this.model.get("track").dataset.id,action:"rerun",tool_id:ac.id},null,function(ad){Galaxy.modal.show({title:ac.get("name")+" is Running",body:ac.get("name")+" is running on the complete dataset. Tool outputs are in dataset's history.",buttons:{Close:function(){Galaxy.modal.hide()}}})})},run_on_region:function(){var ad=this.model.get("track"),ag=this.model,ai=new y.GenomeRegion({chrom:ad.view.chrom,start:ad.view.low,end:ad.view.high}),aj={target_dataset_id:ad.dataset.id,action:"rerun",tool_id:ag.id,regions:[ai.toJSON()]},ah=ad,al=aj.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ak=new P(view,view,{name:this.prefs.name});var af=ah.container.replace_drawable(ah,ak,false);ak.container_div.insertBefore(ah.view.content_div.children()[af]);ak.add_drawable(ah);ah.container_div.appendTo(ak.content_div);ac=ak}else{ac=ah.container}var ae=new ah.constructor(view,ac,{name:al,hda_ldda:"hda"});ae.init_for_tool_data();ae.change_mode(ah.mode);ae.set_filters_manager(ah.filters_manager.copy(ae));ae.update_icons();ac.add_drawable(ae);ae.tiles_div.text("Starting job.");this.run(aj,ae,function(am){ae.set_dataset(new X.Dataset(am));ae.tiles_div.text("Running job.");ae.init()})},run:function(ac,ae,af){ac.inputs=this.model.get_inputs_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_config.root+"api/tools",data:JSON.stringify(ac),dataType:"json",contentType:"application/json",type:"POST"},interval:2000,success_fn:function(ag){return ag!=="pending"}});$.when(ad.go()).then(function(ag){if(ag==="no converter"){ae.container_div.addClass("error");ae.content_div.text(J)}else{if(ag.error){ae.container_div.addClass("error");ae.content_div.text(z+ag.message)}else{af(ag)}}})}});var E=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};E.prototype.gen_val=function(ac){if(this.filter.high===Number.MAX_VALUE||this.filter.low===-Number.MAX_VALUE||this.filter.low===this.filter.high){return this.default_val}return((parseFloat(ac[this.filter.index])-this.filter.low)/(this.filter.high-this.filter.low))};var j=Backbone.Model.extend({initialize:function(ad){var ac={};ab.each(ad.params,function(ae){ac[ae.key]=ae.default_value});if(ad.saved_values){ab.each(this.get("params"),function(ae){if(ae.key in ad.saved_values){ac[ae.key]=ad.saved_values[ae.key]}})}this.set("values",ac)},set_param_default_value:function(ad,ac){var ae=ab.find(this.get("params"),function(af){return af.key===ad});if(ae){ae.default_value=ac}},set_param_value:function(ac,ad){var ae=ab.find(this.get("params"),function(af){return af.key===ac});if(ae){if(typeof ad==="string"||ad instanceof String){if(ad.trim()===""){ad=ae.default_value}else{if(ae.type==="float"){ad=parseFloat(ad)}else{if(ae.type==="int"){ad=parseInt(ad,10)}}}}}if(this.get("values")[ac]!==ad){this.get("values")[ac]=ad;this.trigger("change:values");return true}else{return false}}});var a=Backbone.View.extend({render:function(){var aj=this.model;var ac=$("<div/>").keydown(function(ak){ak.stopPropagation()});var ai;function ah(ao,ak){for(var at=0;at<ao.length;at++){ai=ao[at];if(ai.hidden){continue}var am="param_"+at;var ax=aj.get("values")[ai.key];var az=$("<div class='form-row' />").appendTo(ak);az.append($("<label />").attr("for",am).text(ai.label+":"));if(ai.type==="bool"){az.append($('<input type="checkbox" />').attr("id",am).attr("name",am).attr("checked",ax))}else{if(ai.type==="text"){az.append($('<input type="text"/>').attr("id",am).val(ax).click(function(){$(this).select()}))}else{if(ai.type==="select"){var av=$("<select />").attr("id",am);for(var aq=0;aq<ai.options.length;aq++){$("<option/>").text(ai.options[aq].label).attr("value",ai.options[aq].value).appendTo(av)}av.val(ax);az.append(av)}else{if(ai.type==="color"){var ay=$("<div/>").appendTo(az),au=$("<input />").attr("id",am).attr("name",am).val(ax).css("float","left").appendTo(ay).click(function(aB){$(".tooltip").removeClass("in");var aA=$(this).siblings(".tooltip").addClass("in");aA.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top+Galaxy.modal.scrollTop()-($(aA).height()/2)+($(this).height()/2)}).show();aA.click(function(aC){aC.stopPropagation()});$(document).bind("click.color-picker",function(){aA.hide();$(document).unbind("click.color-picker")});aB.stopPropagation()}),ar=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(ay).attr("title","Set new random color").tooltip(),aw=$("<div class='tooltip right' style='position: absolute;' />").appendTo(ay).hide(),an=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(aw),al=$("<div class='tooltip-arrow'></div>").appendTo(aw),ap=$.farbtastic(an,{width:100,height:100,callback:au,color:ax});ay.append($("<div/>").css("clear","both"));(function(aA){ar.click(function(){aA.setColor(l.get_random_color())})})(ap)}else{az.append($("<input />").attr("id",am).attr("name",am).val(ax))}}}}if(ai.help){az.append($("<div class='help'/>").text(ai.help))}}}ah(aj.get("params"),ac);var ad=this,ag=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ae=function(){ad.update_from_form($(Galaxy.modal.el));Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},af=function(ak){if((ak.keyCode||ak.which)===27){ag()}else{if((ak.keyCode||ak.which)===13){ae()}}};$(window).bind("keypress.check_enter_esc",af);Galaxy.modal.show({title:"Configure",body:ac,buttons:{Cancel:ag,Ok:ae}})},update_from_form:function(ac){var ad=this.model;var ae=false;ab.each(ad.get("params"),function(ah,af){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}ae=ad.set_param_value(ah.key,ag)||ae}})}});var c=function(ac,af,ag,ad,ae){this.track=ac;this.region=af;this.low=af.get("start");this.high=af.get("end");this.w_scale=ag;this.canvas=ad;this.html_elt=$("<div class='track-tile'/>").append(ad);this.data=ae;this.stale=false};c.prototype.predisplay_actions=function(){};var M=function(ac,af,ag,ad,ae){c.call(this,ac,af,ag,ad,ae)};M.prototype.predisplay_actions=function(){};var O=function(af,am,ao,ae,ah,ai,ap,ad,al){c.call(this,af,am,ao,ae,ah);this.mode=ai;this.all_slotted=ad;this.feature_mapper=al;this.has_icons=false;if(ap){this.has_icons=true;var aj=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:F,width:ae.width}).prependTo(this.html_elt);var ak=new y.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),an=ah.length,ag=$("<a/>").addClass("icon more-down").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a/>").addClass("icon more-across").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ag.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.DEEP_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()});ac.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.BROAD_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()})}};q(O.prototype,c.prototype);O.prototype.predisplay_actions=function(){var ad=this,ac={};if(ad.mode!=="Pack"){return}$(this.html_elt).hover(function(){this.hovered=true;$(this).mousemove()},function(){this.hovered=false;$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()}).mousemove(function(ao){if(!this.hovered){return}var aj=$(this).offset(),an=ao.pageX-aj.left,am=ao.pageY-aj.top,at=ad.feature_mapper.get_feature_data(an,am),ak=(at?at[0]:null);$(this).parents(".track-content").children(".overlay").children(".feature-popup").each(function(){if(!ak||$(this).attr("id")!==ak.toString()){$(this).remove()}});if(at){var af=ac[ak];if(!af){var ap={name:at[3],start:at[1],end:at[2],strand:at[4]},ai=ad.track.filters_manager.filters,ah;for(var al=0;al<ai.length;al++){ah=ai[al];ap[ah.name]=at[ah.index]}af=$("<div/>").attr("id",ak).addClass("feature-popup");var au=$("<table/>"),ar,aq,av;for(ar in ap){aq=ap[ar];av=$("<tr/>").appendTo(au);$("<th/>").appendTo(av).text(ar);$("<td/>").attr("align","left").appendTo(av).text(typeof(aq)==="number"?V(aq,2):aq)}af.append($("<div class='feature-popup-inner'>").append(au));ac[ak]=af}af.appendTo($(this).parents(".track-content").children(".overlay"));var ag=an+parseInt(ad.html_elt.css("left"),10)-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"),10)+7;af.css("left",ag+"px").css("top",ae+"px")}else{if(!ao.isPropagationStopped()){ao.stopPropagation();$(this).siblings().each(function(){$(this).trigger(ao)})}}}).mouseleave(function(){$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()})};var g=function(ad,ac,ae){q(ae,{drag_handle_class:"draghandle"});r.call(this,ad,ac,ae);this.dataset=null;if(ae.dataset){this.dataset=(ae.dataset instanceof Backbone.Model?ae.dataset:X.Dataset.findOrCreate(ae.dataset))}this.dataset_check_type="converted_datasets_state";this.data_url_extra_params={};this.data_query_wait=("data_query_wait" in ae?ae.data_query_wait:K);this.data_manager=("data_manager" in ae?ae.data_manager:new y.GenomeDataManager({dataset:this.dataset,genome:new y.Genome({key:ad.dbkey,chroms_info:{chrom_info:ad.chrom_data}}),data_mode_compatible:this.data_and_mode_compatible,can_subset:this.can_subset}));this.min_height_px=16;this.max_height_px=800;this.visible_height_px=this.prefs.height;this.content_div=$("<div class='track-content'>").appendTo(this.container_div);if(this.container){this.container.content_div.append(this.container_div);if(!("resize" in ae)||ae.resize){this.add_resize_handle()}}};q(g.prototype,r.prototype,{action_icons_def:[{name:"mode_icon",title:"Set display mode",css_class:"chevron-expand",on_click_fn:function(){}},r.prototype.action_icons_def[0],{name:"overview_icon",title:"Set as overview",css_class:"overview-icon",on_click_fn:function(ac){ac.view.set_overview(ac)}},r.prototype.action_icons_def[1],{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters()}else{ac.filters_manager.init_filters()}ac.filters_manager.toggle()}},{name:"tools_icon",title:"Tool",css_class:"hammer",on_click_fn:function(ac){ac.tool.toggle();if(ac.tool.is_visible()){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".tooltip").remove()}},{name:"param_space_viz_icon",title:"Tool parameter space visualization",css_class:"arrow-split",on_click_fn:function(ac){var af='<strong>Tool</strong>: <%= track.tool.name %><br/><strong>Dataset</strong>: <%= track.name %><br/><strong>Region(s)</strong>: <select name="regions"><option value="cur">current viewing area</option><option value="bookmarks">bookmarks</option><option value="both">current viewing area and bookmarks</option></select>',ae=ab.template(af,{track:ac});var ah=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new y.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new y.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}Galaxy.modal.hide();window.location.href=galaxy_config.root+"visualization/sweepster?"+$.param({dataset_id:ac.dataset.id,hda_ldda:ac.dataset.get("hda_ldda"),regions:JSON.stringify(new Backbone.Collection(al).toJSON())})},ag=function(ai){if((ai.keyCode||ai.which)===27){ah()}else{if((ai.keyCode||ai.which)===13){ad()}}};Galaxy.modal.show({title:"Visualize tool parameter space and output from different parameter settings?",body:ae,buttons:{No:ah,Yes:ad}})}},r.prototype.action_icons_def[2]],can_draw:function(){return this.dataset&&r.prototype.can_draw.call(this)},build_container_div:function(){return $("<div/>").addClass("track").attr("id","track_"+this.id).css("position","relative")},build_header_div:function(){var ac=$("<div class='track-header'/>");if(this.view.editor){this.drag_div=$("<div/>").addClass(this.drag_handle_class).appendTo(ac)}this.name_div=$("<div/>").addClass("track-name").appendTo(ac).text(this.prefs.name).attr("id",this.prefs.name.replace(/\s+/g,"-").replace(/[^a-zA-Z0-9\-]/g,"").toLowerCase());return ac},set_dataset:function(ac){this.dataset=ac;this.data_manager.set("dataset",ac)},on_resize:function(){this.request_draw({clear_tile_cache:true})},add_resize_handle:function(){var ac=this;var af=false;var ae=false;var ad=$("<div class='track-resize'>");$(ac.container_div).hover(function(){if(ac.prefs.content_visible){af=true;ad.show()}},function(){af=false;if(!ae){ad.hide()}});ad.hide().bind("dragstart",function(ag,ah){ae=true;ah.original_height=$(ac.content_div).height()}).bind("drag",function(ah,ai){var ag=Math.min(Math.max(ai.original_height+ai.deltaY,ac.min_height_px),ac.max_height_px);$(ac.tiles_div).css("height",ag);ac.visible_height_px=(ac.max_height_px===ag?0:ag);ac.on_resize()}).bind("dragend",function(ag,ah){ac.tile_cache.clear();ae=false;if(!af){ad.hide()}ac.config.get("values").height=ac.visible_height_px;ac.changed()}).appendTo(ac.container_div)},set_display_modes:function(af,ai){this.display_modes=af;this.mode=(ai?ai:(this.config&&this.config.get("values").mode?this.config.get("values").mode:this.display_modes[0]));this.action_icons.mode_icon.attr("title","Set display mode (now: "+this.mode+")");var ad=this,ag={};for(var ae=0,ac=ad.display_modes.length;ae<ac;ae++){var ah=ad.display_modes[ae];ag[ah]=function(aj){return function(){ad.change_mode(aj);ad.icons_div.show();ad.container_div.mouseleave(function(){ad.icons_div.hide()})}}(ah)}make_popupmenu(this.action_icons.mode_icon,ag)},build_action_icons:function(){r.prototype.build_action_icons.call(this,this.action_icons_def);if(this.display_modes!==undefined){this.set_display_modes(this.display_modes)}},hide_contents:function(){this.tiles_div.hide();this.container_div.find(".yaxislabel, .track-resize").hide()},show_contents:function(){this.tiles_div.show();this.container_div.find(".yaxislabel, .track-resize").show();this.request_draw()},get_type:function(){if(this instanceof W){return"LabelTrack"}else{if(this instanceof D){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof T){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof d){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.tiles_div.css("height","auto");ad.tiles_div.text("").children().remove();ad.container_div.removeClass("nodata error pending");if(!ad.dataset.id){return}var ac=$.Deferred(),af={hda_ldda:ad.dataset.get("hda_ldda"),data_type:this.dataset_check_type,chrom:ad.view.chrom,retry:ae};$.getJSON(this.dataset.url(),af,function(ag){if(!ag||ag==="error"||ag.kind==="error"){ad.container_div.addClass("error");ad.tiles_div.text(o);if(ag.message){ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("View error").click(function(){Galaxy.modal.show({title:"Trackster Error",body:"<pre>"+ag.message+"</pre>",buttons:{Close:function(){Galaxy.modal.hide()}}})}));ad.tiles_div.append($("<span/>").text(" "));ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("Try again").click(function(){ad.init(true)}))}}else{if(ag==="no converter"){ad.container_div.addClass("error");ad.tiles_div.text(J)}else{if(ag==="no data"||(ag.data!==undefined&&(ag.data===null||ag.data.length===0))){ad.container_div.addClass("nodata");ad.tiles_div.text(G)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(w);setTimeout(function(){ad.init()},ad.data_query_wait)}else{if(ag==="data"||ag.status==="data"){if(ag.valid_chroms){ad.valid_chroms=ag.valid_chroms;ad.update_icons()}ad.tiles_div.text(U);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when.apply($,ad.predraw_init()).done(function(){ac.resolve();ad.container_div.removeClass("nodata error pending");ad.request_draw()})}else{ac.resolve()}}}}}}});this.update_icons();return ac},predraw_init:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){ac.container_div.addClass("line-track");var af=ad.data;if(af&&af.min&&af.max){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.config.set_param_default_value("min_value",ae);ac.config.set_param_default_value("max_value",ag);ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},get_drawables:function(){return this}});var N=function(ae,ad,ag){g.call(this,ae,ad,ag);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in ag?ag.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=(ag.tool?new s(ab.extend(ag.tool,{track:this,tool_state:ag.tool_state})):null);this.tile_cache=new y.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){var af=new aa({model:this.tool});af.render();this.dynamic_tool_div=af.$el;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);if(!this.prefs.content_visible){this.tiles_div.hide()}this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(ag.mode){this.change_mode(ag.mode)}};q(N.prototype,r.prototype,g.prototype,{action_icons_def:g.prototype.action_icons_def.concat([{name:"show_more_rows_icon",title:"To minimize track height, not all feature rows are displayed. Click to display more rows.",css_class:"exclamation",on_click_fn:function(ac){$(".tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw({clear_tile_cache:true})},hide:true}]),copy:function(ac){var ad=this.to_dict();q(ad,{data_manager:this.data_manager});var ae=new this.constructor(this.view,ac,ad);ae.change_mode(this.mode);ae.enabled=this.enabled;return ae},set_filters_manager:function(ac){this.filters_manager=ac;this.header_div.after(this.filters_manager.parent_div)},to_dict:function(){return{track_type:this.get_type(),dataset:{id:this.dataset.id,hda_ldda:this.dataset.get("hda_ldda")},prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},set_min_max:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){var af=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.get("values").mode=ad;if(ad==="Auto"){this.data_manager.clear()}ac.request_draw({clear_tile_cache:true});this.action_icons.mode_icon.attr("title","Set display mode (now: "+ac.mode+")");return ac},update_icons:function(){var ac=this;if(ac.filters_available){ac.action_icons.filters_icon.show()}else{ac.action_icons.filters_icon.hide()}if(ac.tool){ac.action_icons.tools_icon.show();ac.action_icons.param_space_viz_icon.show()}else{ac.action_icons.tools_icon.hide();ac.action_icons.param_space_viz_icon.hide()}},_gen_tile_cache_key:function(ad,ac){return ad+"_"+ac},request_draw:function(ac){if(ac&&ac.clear_tile_cache){this.tile_cache.clear()}this.view.request_redraw(ac,this)},before_draw:function(){this.max_height_px=0},_draw:function(aq){if(!this.can_draw()){return}var an=aq&&aq.clear_after,al=this.view.low,ag=this.view.high,aj=ag-al,ad=this.view.container.width(),ap=this.view.resolution_px_b,af=1/ap;if(this.is_overview){al=this.view.max_low;ag=this.view.max_high;ap=ad/(view.max_high-view.max_low);af=1/ap}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(af*S)),ak,am,ah,ai=[],ao=[];while((ac*S*af)<ag){ak=Math.floor(ac*S*af);am=new y.GenomeRegion({chrom:this.view.chrom,start:ak,end:Math.min(ak+Math.ceil(S*af),this.view.max_high)});ah=this.draw_helper(am,ap,aq);ai.push(ah);$.when(ah).then(function(ar){ao.push(ar)});ac+=1}if(!an){this.tiles_div.children(".remove").removeClass("remove").remove()}var ae=this;$.when.apply($,ai).then(function(){ae.tiles_div.children(".remove").remove();ao=ab.filter(ao,function(ar){return ar!==null});if(ao.length!==0){ae.postdraw_actions(ao,ad,ap,an)}})},_add_yaxis_label:function(af,ah){var ad=this,ag=(af==="max"?"top":"bottom"),ai=(af==="max"?"max":"min"),ac=(af==="max"?"max_value":"min_value"),ae=this.container_div.find(".yaxislabel."+ag);ah=ah||function(){ad.request_draw({clear_tile_cache:true})};if(ae.length!==0){ae.text(ad.prefs[ac])}else{ae=$("<div/>").text(ad.prefs[ac]).make_text_editable({num_cols:12,on_finish:function(aj){$(".tooltip").remove();ad.config.set_param_value(ac,aj);ah()},help_text:"Set "+ai+" value"}).addClass("yaxislabel "+ag).css("color",this.prefs.label_color);this.container_div.prepend(ae)}},postdraw_actions:function(af,ag,ai,ac){var ae=ab.filter(af,function(aj){return(aj instanceof M)});if(ae.length>0){this.max_height_px=0;var ad=this;ab.each(af,function(aj){if(!(aj instanceof M)){aj.html_elt.remove();ad.draw_helper(aj.region,ai,{force:true,mode:"Coverage"})}});ad._add_yaxis_label("max")}else{this.container_div.find(".yaxislabel").remove();var ah=ab.find(af,function(aj){return aj.has_icons});if(ah){ab.each(af,function(aj){if(!aj.has_icons){aj.html_elt.css("padding-top",F)}})}}},get_mode:function(ac){return this.mode},update_auto_mode:function(ac){},_get_drawables:function(){return[this]},draw_helper:function(al,an,ao){if(!ao){ao={}}var ad=ao.force,ai=ao.mode||this.mode,af=1/an,ae=this,ag=this._get_drawables(),am=this._gen_tile_cache_key(an,al),ah=function(ap){return(ap&&"track" in ap)};var aj=(ad?undefined:ae.tile_cache.get_elt(am));if(aj){if(ah(aj)){ae.show_tile(aj,an)}return aj}if(ao.data_fetch===false){return null}var ak=function(){var ap=(ab.find(C,function(ar){return ar===ai})?"Coverage":ai);var aq=ab.map(ag,function(ar){return ar.data_manager.get_data(al,ap,af,ae.data_url_extra_params)});if(view.reference_track){aq.push(view.reference_track.data_manager.get_data(al,ai,af,view.reference_track.data_url_extra_params))}return aq};var ac=$.Deferred();ae.tile_cache.set_elt(am,ac);$.when.apply($,ak()).then(function(){var ap=ak(),av=ap,aB;if(view.reference_track){aB=view.reference_track.data_manager.subset_entry(ap.pop(),al)}var aw=[],at=[];ab.each(ag,function(aG,aD){var aF=aG.mode,aE=av[aD];if(aF==="Auto"){aF=aG.get_mode(aE);aG.update_auto_mode(aF)}aw.push(aF);at.push(aG.get_canvas_height(aE,aF,an,aq))});var au=ae.view.canvas_manager.new_canvas(),ax=al.get("start"),aC=al.get("end"),ar=0,aq=Math.ceil((aC-ax)*an)+ae.left_offset,az=ab.max(at),ay;au.width=aq;au.height=(ao.height||az);var aA=au.getContext("2d");aA.translate(ae.left_offset,0);if(ag.length>1){aA.globalAlpha=0.5;aA.globalCompositeOperation="source-over"}ab.each(ag,function(aE,aD){ay=aE.draw_tile(av[aD],aA,aw[aD],al,an,aB)});if(ay!==undefined){ae.tile_cache.set_elt(am,ay);ae.show_tile(ay,an)}ac.resolve(ay)});return ac},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_line_track_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.LinePainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new M(this,ag,ai,af,ac.data)},draw_tile:function(ac,ad,ag,af,ah,ae){},show_tile:function(ae,ah){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ah;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{this.tiles_div.append(ac)}ac.css("height","auto");this.max_height_px=Math.max(this.max_height_px,ac.height());ac.parent().children().css("height",this.max_height_px+"px");var af=this.max_height_px;if(this.visible_height_px!==0){af=Math.min(this.max_height_px,this.visible_height_px)}this.tiles_div.css("height",af+"px")},tool_region_and_parameters_str:function(af){var ac=this,ae=(af!==undefined?af.toString():"all"),ad=ab.values(ac.tool.get_inputs_dict()).join(", ");return" - region=["+ae+"], parameters=["+ad+"]"},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="bigwig"}else{if(ac.dataset_type==="bigwig"||ac.extra_info==="no_detail"){return false}else{return true}}}},can_subset:function(ac){if(ac.message||ac.extra_info==="no_detail"){return false}else{if(ac.dataset_type==="bigwig"){return(ac.data[1][0]-ac.data[0][0]===1)}}return true},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state"}});var W=function(ad,ac){var ae={resize:false};g.call(this,ad,ac,ae);this.container_div.addClass("label-track")};q(W.prototype,g.prototype,{build_header_div:function(){},init:function(){this.enabled=true},predraw_init:function(){},_draw:function(ag){var ae=this.view,af=ae.high-ae.low,aj=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/aj)*aj,ah=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ai=(ac-ae.low)/af*ah;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ai-1}));ac+=aj}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){N.call(this,ad,ac,ag);this.drawables=[];if("drawables" in ag){var af;for(var ae=0;ae<ag.drawables.length;ae++){af=ag.drawables[ae];this.drawables[ae]=p(af,ad,null);if(af.left_offset>this.left_offset){this.left_offset=af.left_offset}}this.enabled=true}ab.each(this.drawables,function(ah){if(ah instanceof d||ah instanceof T){ah.change_mode("Coverage")}});this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,N.prototype,{display_modes:C,action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_group()}}].concat(N.prototype.action_icons_def),to_dict:A.prototype.to_dict,add_drawable:A.prototype.add_drawable,unpack_drawables:A.prototype.unpack_drawables,change_mode:function(ac){N.prototype.change_mode.call(this,ac);for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].change_mode(ac)}},init:function(){var ae=[];for(var ad=0;ad<this.drawables.length;ad++){ae.push(this.drawables[ad].init())}var ac=this;$.when.apply($,ae).then(function(){ac.enabled=true;ac.request_draw()})},update_icons:function(){this.action_icons.filters_icon.hide();this.action_icons.tools_icon.hide();this.action_icons.param_space_viz_icon.hide()},can_draw:r.prototype.can_draw,_get_drawables:function(){return this.drawables},show_group:function(){var af=new P(this.view,this.container,{name:this.prefs.name}),ac;for(var ae=0;ae<this.drawables.length;ae++){ac=this.drawables[ae];ac.update_icons();af.add_drawable(ac);ac.container=af;af.content_div.append(ac.container_div)}var ad=this.container.replace_drawable(this,af,true);af.request_draw({clear_tile_cache:true})},before_draw:function(){N.prototype.before_draw.call(this);var ad=ab.min(ab.map(this.drawables,function(ae){return ae.prefs.min_value})),ac=ab.max(ab.map(this.drawables,function(ae){return ae.prefs.max_value}));this.prefs.min_value=ad;this.prefs.max_value=ac;ab.each(this.drawables,function(ae){ae.prefs.min_value=ad;ae.prefs.max_value=ac})},update_all_min_max:function(){var ac=this;ab.each(this.drawables,function(ad){ad.prefs.min_value=ac.prefs.min_value;ad.prefs.max_value=ac.prefs.max_value});this.request_draw({clear_tile_cache:true})},postdraw_actions:function(ai,ac,al,ah){N.prototype.postdraw_actions.call(this,ai,ac,al,ah);var ag=-1,ae;for(ae=0;ae<ai.length;ae++){var aj=ai[ae].html_elt.find("canvas").height();if(aj>ag){ag=aj}}for(ae=0;ae<ai.length;ae++){var af=ai[ae];if(af.html_elt.find("canvas").height()!==ag){this.draw_helper(af.region,al,{force:true,height:ag});af.html_elt.remove()}}var ad=this,ak=function(){ad.update_all_min_max()};this._add_yaxis_label("min",ak);this._add_yaxis_label("max",ak)}});var D=function(ac){N.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});this.left_offset=ac.canvas_manager.char_width_px;this.container_div.addClass("reference-track");this.data_url=galaxy_config.root+"api/genomes/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new y.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(D.prototype,r.prototype,N.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"height",type:"int",default_value:13,hidden:true}]),build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},predraw_init:function(){},can_draw:r.prototype.can_draw,draw_helper:function(ad,ae,ac){if(ae>this.view.canvas_manager.char_width_px){this.tiles_div.show();return N.prototype.draw_helper.call(this,ad,ae,ac)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(ae,ak,af,ah,al){var ad=this.data_manager.subset_entry(ae,ah),aj=ad.data;var ac=ak.canvas;ak.font=ak.canvas.manager.default_font;ak.textAlign="center";for(var ag=0,ai=aj.length;ag<ai;ag++){ak.fillStyle=this.view.get_base_color(aj[ag]);ak.fillText(aj[ag],Math.floor(ag*al),10)}return new c(this,ah,al,ac,ad)}});var h=function(ad,ac,ae){this.mode="Histogram";N.call(this,ad,ac,ae)};q(h.prototype,r.prototype,N.prototype,{display_modes:C,config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Color",type:"color",default_value:l.get_random_color()},{key:"min_value",label:"Min Value",type:"float",default_value:undefined},{key:"max_value",label:"Max Value",type:"float",default_value:undefined},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:30,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},before_draw:function(){},draw_tile:function(ac,ad,af,ae,ag){return this._draw_line_track_tile(ac,ad,af,ae,ag)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)},postdraw_actions:function(ad,ae,af,ac){this._add_yaxis_label("max");this._add_yaxis_label("min")}});var t=function(ad,ac,ae){this.mode="Heatmap";N.call(this,ad,ac,ae)};q(t.prototype,r.prototype,N.prototype,{display_modes:["Heatmap"],config_params:ab.union(r.prototype.config_params,[{key:"pos_color",label:"Positive Color",type:"color",default_value:"#FF8C00"},{key:"neg_color",label:"Negative Color",type:"color",default_value:"#4169E1"},{key:"min_value",label:"Min Value",type:"float",default_value:-1},{key:"max_value",label:"Max Value",type:"float",default_value:1},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:500,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new c(this,ag,ai,af,ac.data)}});var d=function(ad,ac,ae){N.call(this,ad,ac,ae);this.container_div.addClass("feature-track");this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(d.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true,help:"Show the number of items in each bin when drawing summary histogram"},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"connector_style",label:"Connector style",type:"select",default_value:"fishbones",options:[{label:"Line with arrows",value:"fishbone"},{label:"Arcs",value:"arcs"}]},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.set_painter_from_config();this.request_draw({clear_tile_cache:true})},set_painter_from_config:function(){if(this.config.get("values").connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},postdraw_actions:function(am,ae,an,al){N.prototype.postdraw_actions.call(this,am,ae,an,al);var ag=this,ah;if(ag.filters_manager){var af=ag.filters_manager.filters,aj;for(aj=0;aj<af.length;aj++){af[aj].update_ui_elt()}var ai=false,ak,ad;for(ah=0;ah<am.length;ah++){if(am[ah].data.length){ak=am[ah].data[0];for(aj=0;aj<af.length;aj++){ad=af[aj];if(ad.applies_to(ak)&&ad.min!==ad.max){ai=true;break}}}}if(ag.filters_available!==ai){ag.filters_available=ai;if(!ag.filters_available){ag.filters_manager.hide()}ag.update_icons()}}if(am[0] instanceof O){var ac=true;for(ah=0;ah<am.length;ah++){if(!am[ah].all_slotted){ac=false;break}}if(!ac){this.action_icons.show_more_rows_icon.show()}else{this.action_icons.show_more_rows_icon.hide()}}else{this.action_icons.show_more_rows_icon.hide()}},update_auto_mode:function(ac){if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}this.action_icons.mode_icon.attr("title","Set display mode (now: Auto/"+ac+")")}},incremental_slots:function(ag,ac,af){var ad=this.view.canvas_manager.dummy_context,ae=this.slotters[ag];if(!ae||(ae.mode!==af)){ae=new (u.FeatureSlotter)(ag,af,B,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.extra_info==="no_detail"||this.is_overview){mode="no_detail"}else{if(this.view.high-this.view.low>I){mode="Squish"}else{mode="Pack"}}return mode},get_canvas_height:function(ac,ag,ah,ad){if(ag==="Coverage"||ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var af=this.incremental_slots(ah,ac.data,ag);var ae=new (this.painter)(null,null,null,this.prefs,ag);return Math.max(this.min_height_px,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,af,aj,ae){var ap=this,ad=aq.canvas,ax=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(am.dataset_type==="bigwig"){return this._draw_line_track_tile(am,aq,ao,af,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var ar=0,au=am.data.length;ar<au;ar++){var ah=am.data[ar];var at=false;var al;for(var aw=0,aB=ak.length;aw<aB;aw++){al=ak[aw];al.update_attrs(ah);if(!al.keep(ah)){at=true;break}}if(!at){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aA=(this.filters_manager.alpha_filter?new E(this.filters_manager.alpha_filter):null),ay=(this.filters_manager.height_filter?new E(this.filters_manager.height_filter):null),az=new (this.painter)(ai,ax,ac,this.prefs,ao,aA,ay,ae,function(aC){return ap.view.get_base_color(aC)});var av=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){av=az.draw(aq,ad.width,ad.height,aj,an);av.translation=-ag}return new O(ap,af,aj,ad,am.data,ao,am.message,all_slotted,av)}});var Z=function(ad,ac,ae){N.call(this,ad,ac,ae);this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Histogram color",type:"color",default_value:l.get_random_color()},{key:"show_sample_data",label:"Show sample data",type:"bool",default_value:true},{key:"show_labels",label:"Show summary and sample labels",type:"bool",default_value:true},{key:"summary_height",label:"Locus summary height",type:"float",default_value:20},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,af,ah,ag,ai){if(ac.dataset_type==="bigwig"){return this._draw_line_track_tile(ac,af,"Histogram",ag,ai)}else{var ae=this.view,ad=new (this.painter)(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah,function(aj){return ae.get_base_color(aj)});ad.draw(af,af.canvas.width,af.canvas.height,ai);return new c(this,ag,ai,af.canvas,ac.data)}},get_canvas_height:function(ac,ag,ah,ae){if(ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var ad=(this.dataset.get_metadata("sample_names")?this.dataset.get_metadata("sample_names").length:0);if(ad===0&&ac.data.length!==0){ad=ac.data[0][7].match(/,/g);if(ad===null){ad=1}else{ad=ad.length+1}}var af=new (this.painter)(null,null,null,this.prefs,ag);return af.get_required_height(ad)}},predraw_init:function(){var ac=[g.prototype.predraw_init.call(this)];if(!this.dataset.get_metadata("sample_names")){ac.push(this.dataset.fetch())}return ac},postdraw_actions:function(ag,ah,aj,ad){N.prototype.postdraw_actions.call(this,ag,ah,aj,ad);var af=ab.filter(ag,function(ak){return(ak instanceof M)});var ae=this.dataset.get_metadata("sample_names");if(af.length===0&&this.prefs.show_labels&&ae){var ac;if(this.container_div.find(".yaxislabel.variant").length===0){ac=this.prefs.summary_height/2;this.tiles_div.prepend($("<div/>").text("Summary").addClass("yaxislabel variant top").css({"font-size":ac+"px",top:(this.prefs.summary_height-ac)/2+"px"}));if(this.prefs.show_sample_data){var ai=ae.join("<br/>");this.tiles_div.prepend($("<div/>").html(ai).addClass("yaxislabel variant top sample").css({top:this.prefs.summary_height+2,}))}}ac=(this.mode==="Squish"?5:10)+"px";$(this.tiles_div).find(".sample").css({"font-size":ac,"line-height":ac});$(this.tiles_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel.variant").remove()}}});var T=function(ad,ac,ae){d.call(this,ad,ac,ae);this.painter=(ad.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(T.prototype,r.prototype,N.prototype,d.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block and sense strand color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_insertions",label:"Show insertions",type:"bool",default_value:false},{key:"show_differences",label:"Show differences only",type:"bool",default_value:true},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})}});var e={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:d,LineTrack:h,ReadTrack:T,VariantTrack:Z,VcfTrack:Z};var p=function(ae,ad,ac){if("copy" in ae){return ae.copy(ac)}else{var af=ae.obj_type;if(!af){af=ae.track_type}return new e[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:d,DiagonalHeatmapTrack:t,ReadTrack:T,VariantTrack:Z,CompositeTrack:f,object_from_template:p}});
\ No newline at end of file
diff -r 100a64a1d85cbb582bd83ab9bbdd6cbd73a566f2 -r 8ae19975dd333c6b4b4c15f93a0350a24f3c10db static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -3384,9 +3384,11 @@
}
// -- Update track, tile heights based on new tile. --
+
+ tile_element.css('height', 'auto');
- // Update max height based on current tile's canvas.
- this.max_height_px = Math.max(this.max_height_px, $(tile.canvas).height());
+ // Update max height based on current tile's height.
+ this.max_height_px = Math.max(this.max_height_px, tile_element.height());
// Update height for all tiles based on max height.
tile_element.parent().children().css("height", this.max_height_px + "px");
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.
1
0
2 new commits in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/17b09bab9eea/
Changeset: 17b09bab9eea
User: remy_d1
Date: 2013-03-05 17:22:20
Summary: add userskeys feature/controller which is usefull to manage user's API key through admin panel
Affected #: 4 files
diff -r dbe53e2c1eab2b377880e87c4d2bd770dc470b80 -r 17b09bab9eead7e90f0981cdeee033dd860df72a lib/galaxy/webapps/galaxy/controllers/userskeys.py
--- /dev/null
+++ b/lib/galaxy/webapps/galaxy/controllers/userskeys.py
@@ -0,0 +1,108 @@
+"""
+Contains the user interface in the Universe class
+"""
+
+import glob
+import logging
+import os
+import socket
+import string
+import random
+import pprint
+
+from galaxy import web
+from galaxy import util, model
+from galaxy.model.orm import and_
+from galaxy.security.validate_user_input import validate_email, validate_publicname, validate_password, transform_publicname
+from galaxy.util.json import from_json_string, to_json_string
+from galaxy.web import url_for
+from galaxy.web.base.controller import BaseUIController, UsesFormDefinitionsMixin
+from galaxy.web.form_builder import CheckboxField, build_select_field
+from galaxy.web.framework.helpers import time_ago, grids
+
+from inspect import getmembers
+
+log = logging.getLogger( __name__ )
+
+require_login_template = """
+<p>
+ This %s has been configured such that only users who are logged in may use it.%s
+</p>
+<p/>
+"""
+
+class UserOpenIDGrid( grids.Grid ):
+ use_panels = False
+ title = "OpenIDs linked to your account"
+ model_class = model.UserOpenID
+ template = '/user/openid_manage.mako'
+ default_filter = { "openid" : "All" }
+ default_sort_key = "-create_time"
+ columns = [
+ grids.TextColumn( "OpenID URL", key="openid", link=( lambda x: dict( action='openid_auth', login_button="Login", openid_url=x.openid if not x.provider else '', openid_provider=x.provider, auto_associate=True ) ) ),
+ grids.GridColumn( "Created", key="create_time", format=time_ago ),
+ ]
+ operations = [
+ grids.GridOperation( "Delete", async_compatible=True ),
+ ]
+ def build_initial_query( self, trans, **kwd ):
+ return trans.sa_session.query( self.model_class ).filter( self.model_class.user_id == trans.user.id )
+
+class User( BaseUIController, UsesFormDefinitionsMixin ):
+ user_openid_grid = UserOpenIDGrid()
+ installed_len_files = None
+
+
+ @web.expose
+ @web.require_login()
+ @web.require_admin
+ def index( self, trans, cntrller, **kwd ):
+ return trans.fill_template( 'webapps/galaxy/user/list_users.mako', action='all_users', cntrller=cntrller )
+
+
+
+ @web.expose
+ @web.require_login()
+ @web.require_admin
+ def api_keys( self, trans, cntrller, uid, **kwd ):
+ params = util.Params( kwd )
+ message = util.restore_text( params.get( 'message', '' ) )
+ status = params.get( 'status', 'done' )
+ uid = params.get('uid', uid)
+ pprint.pprint(uid)
+ if params.get( 'new_api_key_button', False ):
+ new_key = trans.app.model.APIKeys()
+ new_key.user_id = uid
+ new_key.key = trans.app.security.get_new_guid()
+ trans.sa_session.add( new_key )
+ trans.sa_session.flush()
+ message = "Generated a new web API key"
+ status = "done"
+ return trans.fill_template( 'webapps/galaxy/user/ok_admin_api_keys.mako',
+ cntrller=cntrller,
+ message=message,
+ status=status )
+
+
+ @web.expose
+ @web.require_login()
+ @web.require_admin
+ def all_users( self, trans, cntrller="userskeys", **kwd ):
+ params = util.Params( kwd )
+ message = util.restore_text( params.get( 'message', '' ) )
+ status = params.get( 'status', 'done' )
+ users = []
+ for user in trans.sa_session.query( trans.app.model.User ) \
+ .filter( trans.app.model.User.table.c.deleted==False ) \
+ .order_by( trans.app.model.User.table.c.email ):
+ uid = int(user.id)
+ userkey = ""
+ for api_user in trans.sa_session.query(trans.app.model.APIKeys) \
+ .filter( trans.app.model.APIKeys.user_id == uid):
+ userkey = api_user.key
+ users.append({'uid':uid, 'email':user.email, 'key':userkey})
+ return trans.fill_template( 'webapps/galaxy/user/list_users.mako',
+ cntrller=cntrller,
+ users=users,
+ message=message,
+ status=status )
diff -r dbe53e2c1eab2b377880e87c4d2bd770dc470b80 -r 17b09bab9eead7e90f0981cdeee033dd860df72a templates/webapps/galaxy/admin/index.mako
--- a/templates/webapps/galaxy/admin/index.mako
+++ b/templates/webapps/galaxy/admin/index.mako
@@ -45,6 +45,7 @@
<div class="toolTitle"><a href="${h.url_for( controller='admin', action='users' )}" target="galaxy_main">Manage users</a></div><div class="toolTitle"><a href="${h.url_for( controller='admin', action='groups' )}" target="galaxy_main">Manage groups</a></div><div class="toolTitle"><a href="${h.url_for( controller='admin', action='roles' )}" target="galaxy_main">Manage roles</a></div>
+ <div class="toolTitle"><a href="${h.url_for( controller='userskeys', action='all_users' )}" target="galaxy_main">Manage users API keys</a></div>
%if trans.app.config.allow_user_impersonation:
<div class="toolTitle"><a href="${h.url_for( controller='admin', action='impersonate' )}" target="galaxy_main">Impersonate a user</a></div>
%endif
diff -r dbe53e2c1eab2b377880e87c4d2bd770dc470b80 -r 17b09bab9eead7e90f0981cdeee033dd860df72a templates/webapps/galaxy/user/list_users.mako
--- /dev/null
+++ b/templates/webapps/galaxy/user/list_users.mako
@@ -0,0 +1,37 @@
+<%inherit file="/base.mako"/>
+
+%if message:
+ ${render_msg( message, status )}
+%endif
+
+
+%if users:
+ <div class="toolForm">
+ <div class="toolFormTitle">Users informations</div>
+ <table>
+ <thead><th>UID</th><th>email</th></thead>
+ <tbody>
+ %for user in users:
+ <tr>
+ <td>${user['uid']}</td>
+ <td>${user['email']}</td>
+ <td>${user['key']}</td>
+ <td>
+ <form action="${h.url_for( controller='userskeys', action='api_keys', cntrller=cntrller )}" method="POST">
+ <input type="hidden" name="uid" value=${user['uid']} />
+ <input type="submit" name="new_api_key_button" value="Generate a new key now" />
+ </form>
+ </td>
+ </tr>
+ %endfor
+ </tbody>
+ </table>
+ <div style="clear: both"></div>
+ </div>
+%else:
+ <div>No informations available</div>
+%endif
+
+
+<p/>
+
diff -r dbe53e2c1eab2b377880e87c4d2bd770dc470b80 -r 17b09bab9eead7e90f0981cdeee033dd860df72a templates/webapps/galaxy/user/ok_admin_api_keys.mako
--- /dev/null
+++ b/templates/webapps/galaxy/user/ok_admin_api_keys.mako
@@ -0,0 +1,28 @@
+<%inherit file="/base.mako"/>
+<%namespace file="/message.mako" import="render_msg" />
+
+<br/><br/>
+<ul class="manage-table-actions">
+ <li>
+ <a class="action-button" href="${h.url_for( controller='userskeys', action='all_users', cntrller=cntrller )}">List users API keys</a>
+ </li>
+</ul>
+
+%if message:
+ ${render_msg( message, status )}
+%endif
+
+ <div>
+ <div style="clear: both;">
+ SUCCESS. A new API key has been generated.
+ </div>
+
+
+ <div style="clear: both;">
+ An API key will allow you to access Galaxy via its web
+ API (documentation forthcoming). Please note that
+ <strong>this key acts as an alternate means to access
+ your account, and should be treated with the same care
+ as your login password</strong>.
+ </div>
+ </div>
https://bitbucket.org/galaxy/galaxy-central/commits/a1a06f6deb41/
Changeset: a1a06f6deb41
User: remy_d1
Date: 2013-03-05 17:50:40
Summary: modified method name 'api_keys' to 'admin_api_keys' for user vs userskeys controller
Affected #: 2 files
diff -r 17b09bab9eead7e90f0981cdeee033dd860df72a -r a1a06f6deb410e1c50b4cb86c28e97a75df4f91b lib/galaxy/webapps/galaxy/controllers/userskeys.py
--- a/lib/galaxy/webapps/galaxy/controllers/userskeys.py
+++ b/lib/galaxy/webapps/galaxy/controllers/userskeys.py
@@ -64,7 +64,7 @@
@web.expose
@web.require_login()
@web.require_admin
- def api_keys( self, trans, cntrller, uid, **kwd ):
+ def admin_api_keys( self, trans, cntrller, uid, **kwd ):
params = util.Params( kwd )
message = util.restore_text( params.get( 'message', '' ) )
status = params.get( 'status', 'done' )
diff -r 17b09bab9eead7e90f0981cdeee033dd860df72a -r a1a06f6deb410e1c50b4cb86c28e97a75df4f91b templates/webapps/galaxy/user/list_users.mako
--- a/templates/webapps/galaxy/user/list_users.mako
+++ b/templates/webapps/galaxy/user/list_users.mako
@@ -17,7 +17,7 @@
<td>${user['email']}</td><td>${user['key']}</td><td>
- <form action="${h.url_for( controller='userskeys', action='api_keys', cntrller=cntrller )}" method="POST">
+ <form action="${h.url_for( controller='userskeys', action='admin_api_keys', cntrller=cntrller )}" method="POST"><input type="hidden" name="uid" value=${user['uid']} /><input type="submit" name="new_api_key_button" value="Generate a new key now" /></form>
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.
1
0
2 new commits in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/3d138ced1f26/
Changeset: 3d138ced1f26
Branch: next-stable
User: jgoecks
Date: 2013-10-22 00:41:45
Summary: Pack script.
Affected #: 1 file
diff -r 14fbaad2645bd7b8a0a2f9a4a682b38ecf18c7d0 -r 3d138ced1f26c810a24bead0aa8fa6d8a65a7812 static/scripts/packed/viz/trackster/tracks.js
--- a/static/scripts/packed/viz/trackster/tracks.js
+++ b/static/scripts/packed/viz/trackster/tracks.js
@@ -1,1 +1,1 @@
-define(["libs/underscore","viz/visualization","viz/trackster/util","viz/trackster/slotting","viz/trackster/painters","viz/trackster/filters","mvc/data","mvc/tools"],function(ab,y,l,u,L,i,X,R){var q=ab.extend;var n={};var k=function(ac,ad){n[ac.attr("id")]=ad};var m=function(ac,ae,ag,af){ag=".group";var ad={};n[ac.attr("id")]=af;ac.bind("drag",{handle:"."+ae,relative:true},function(ao,ap){var an=$(this),at=$(this).parent(),ak=at.children(),am=n[$(this).attr("id")],aj,ai,aq,ah,al;ai=$(this).parents(ag);if(ai.length!==0){aq=ai.position().top;ah=aq+ai.outerHeight();var ar=n[ai.attr("id")];if(ap.offsetY<aq){$(this).insertBefore(ai);ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);ar.remove_drawable(am);ar.container.add_drawable(am);return}}}ai=null;for(al=0;al<ak.length;al++){aj=$(ak.get(al));aq=aj.position().top;ah=aq+aj.outerHeight();if(aj.is(ag)&&this!==aj.get(0)&&ap.offsetY>=aq&&ap.offsetY<=ah){if(ap.offsetY-aq<ah-ap.offsetY){aj.find(".content-div").prepend(this)}else{aj.find(".content-div").append(this)}if(am.container){am.container.remove_drawable(am)}n[aj.attr("id")].add_drawable(am);return}}for(al=0;al<ak.length;al++){aj=$(ak.get(al));if(ap.offsetY<aj.position().top&&!(aj.hasClass("reference-track")||aj.hasClass("intro"))){break}}if(al===ak.length){if(this!==ak.get(al-1)){at.append(this);n[at.attr("id")].move_drawable(am,al)}}else{if(this!==ak.get(al)){$(this).insertBefore(ak.get(al));n[at.attr("id")].move_drawable(am,(ap.deltaY>0?al-1:al))}}}).bind("dragstart",function(){ad["border-top"]=ac.css("border-top");ad["border-bottom"]=ac.css("border-bottom");$(this).css({"border-top":"1px solid blue","border-bottom":"1px solid blue"})}).bind("dragend",function(){$(this).css(ad)})};var F=20,B=100,I=12000,S=400,K=5000,x=100,o="Cannot display dataset due to an error. ",J="A converter for this dataset is not installed. Please check your datatypes_conf.xml file.",G="No data for this chrom/contig.",w="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",z="Tool cannot be rerun: ",b="Loading data...",U="Ready for display",Q=10,H=20,C=["Histogram","Line","Filled","Intensity"];function V(ad,ac){if(!ac){ac=0}var ae=Math.pow(10,ac);return Math.round(ad*ae)/ae}var r=function(ad,ac,af){if(!r.id_counter){r.id_counter=0}this.id=r.id_counter++;this.view=ad;this.container=ac;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.config=new j({params:this.config_params,onchange:this.config_onchange,saved_values:af.prefs});this.prefs=this.config.get("values");if(!this.prefs.name){this.prefs.name=af.name}if(this.config_onchange){this.config.on("change:values",this.config_onchange,this)}this.container_div=this.build_container_div();this.header_div=this.build_header_div();if(this.header_div){this.container_div.append(this.header_div);this.icons_div=$("<div/>").css("float","left").hide().appendTo(this.header_div);this.build_action_icons(this.action_icons_def);this.header_div.append($("<div style='clear: both'/>"));this.header_div.dblclick(function(ag){ag.stopPropagation()});var ae=this;this.container_div.hover(function(){ae.icons_div.show()},function(){ae.icons_div.hide()});$("<div style='clear: both'/>").appendTo(this.container_div)}};r.prototype.action_icons_def=[{name:"toggle_icon",title:"Hide/show content",css_class:"toggle",on_click_fn:function(ac){if(ac.prefs.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.prefs.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.prefs.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var ac=new a({model:ad.config});ac.render()}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".tooltip").remove();ac.remove()}}];q(r.prototype,{config_params:[{key:"name",label:"Name",type:"text",default_value:""},{key:"content_visible",type:"bool",default_value:true,hidden:true}],config_onchange:function(){this.track.set_name(this.track.config.get("values").name)},init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.prefs.content_visible){return true}return false},request_draw:function(){},_draw:function(ac){},to_dict:function(){},set_name:function(ac){this.old_name=this.prefs.name;this.prefs.name=ac;this.name_div.text(this.prefs.name)},revert_name:function(){if(this.old_name){this.prefs.name=this.old_name;this.name_div.text(this.prefs.name)}},remove:function(){this.changed();this.container.remove_drawable(this);var ac=this.view;this.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})},build_container_div:function(){},build_header_div:function(){},add_action_icon:function(ad,ai,ah,ag,ac,af){var ae=this;this.action_icons[ad]=$("<a/>").attr("title",ai).addClass("icon-button").addClass(ah).tooltip().click(function(){ag(ae)}).appendTo(this.icons_div);if(af){this.action_icons[ad].hide()}},build_action_icons:function(ac){var ae;for(var ad=0;ad<ac.length;ad++){ae=ac[ad];this.add_action_icon(ae.name,ae.title,ae.css_class,ae.on_click_fn,ae.prepend,ae.hide)}},update_icons:function(){},hide_contents:function(){},show_contents:function(){},get_drawables:function(){}});var A=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(A.prototype,r.prototype,{unpack_drawables:function(ae){this.drawables=[];var ad;for(var ac=0;ac<ae.length;ac++){ad=p(ae[ac],this.view,this);this.add_drawable(ad)}},init:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].init()}},_draw:function(ac){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad]._draw(ac)}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{prefs:this.prefs,obj_type:this.obj_type,drawables:ad}},add_drawable:function(ac){this.drawables.push(ac);ac.container=this;this.changed()},add_drawable_before:function(ae,ac){this.changed();var ad=this.drawables.indexOf(ac);if(ad!==-1){this.drawables.splice(ad,0,ae);return true}return false},replace_drawable:function(ae,ac,ad){var af=this.drawables.indexOf(ae);if(af!==-1){this.drawables[af]=ac;if(ad){ae.container_div.replaceWith(ac.container_div)}this.changed()}return af},remove_drawable:function(ad){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);ad.container=null;this.changed();return true}return false},move_drawable:function(ad,ae){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);this.drawables.splice(ae,0,ad);this.changed();return true}return false},get_drawables:function(){return this.drawables},get_tracks:function(af){var ac=this.drawables.slice(0),ad=[],ae;while(ac.length!==0){ae=ac.shift();if(ae instanceof af){ad.push(ae)}else{if(ae.drawables){ac=ac.concat(ae.drawables)}}}return ad}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});A.call(this,ad,ac,af);this.content_div=$("<div/>").addClass("content-div").attr("id","group_"+this.id+"_content_div").appendTo(this.container_div);k(this.container_div,this);k(this.content_div,this);m(this.container_div,this.drag_handle_class,".group",this);this.filters_manager=new i.FiltersManager(this);this.header_div.after(this.filters_manager.parent_div);this.saved_filters_managers=[];if("drawables" in af){this.unpack_drawables(af.drawables)}if("filters" in af){var ae=this.filters_manager;this.filters_manager=new i.FiltersManager(this,af.filters);ae.parent_div.replaceWith(this.filters_manager.parent_div);if(af.filters.visible){this.setup_multitrack_filtering()}}};q(P.prototype,r.prototype,A.prototype,{action_icons_def:[r.prototype.action_icons_def[0],r.prototype.action_icons_def[1],{name:"composite_icon",title:"Show composite track",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_composite_track()}},{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters();ac._restore_filter_managers()}else{ac.setup_multitrack_filtering();ac.request_draw({clear_tile_cache:true})}ac.filters_manager.toggle()}},r.prototype.action_icons_def[2]],build_container_div:function(){var ac=$("<div/>").addClass("group").attr("id","group_"+this.id);if(this.container){this.container.content_div.append(ac)}return ac},build_header_div:function(){var ac=$("<div/>").addClass("track-header");ac.append($("<div/>").addClass(this.drag_handle_class));this.name_div=$("<div/>").addClass("track-name").text(this.prefs.name).appendTo(ac);return ac},hide_contents:function(){this.tiles_div.hide()},show_contents:function(){this.tiles_div.show();this.request_draw()},update_icons:function(){var ae=this.drawables.length;if(ae===0){this.action_icons.composite_icon.hide();this.action_icons.filters_icon.hide()}else{if(ae===1){if(this.drawables[0] instanceof f){this.action_icons.composite_icon.show()}this.action_icons.filters_icon.hide()}else{var al,ak,ai,ao=true,ag=this.drawables[0].get_type(),ac=0;for(al=0;al<ae;al++){ai=this.drawables[al];if(ai.get_type()!==ag){can_composite=false;break}if(ai instanceof d){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".tooltip").remove()}if(ac>1&&ac===this.drawables.length){var ap={},ad;ai=this.drawables[0];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];ap[ad.name]=[ad]}for(al=1;al<this.drawables.length;al++){ai=this.drawables[al];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];if(ad.name in ap){ap[ad.name].push(ad)}}}this.filters_manager.remove_all();var af,ah,aj,am;for(var an in ap){af=ap[an];if(af.length===ac){ah=new i.NumberFilter({name:af[0].name,index:af[0].index});this.filters_manager.add_filter(ah)}}if(this.filters_manager.filters.length>0){this.action_icons.filters_icon.show()}else{this.action_icons.filters_icon.hide()}}else{this.action_icons.filters_icon.hide()}}}},_restore_filter_managers:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].filters_manager=this.saved_filters_managers[ac]}this.saved_filters_managers=[]},setup_multitrack_filtering:function(){if(this.filters_manager.filters.length>0){this.saved_filters_managers=[];for(var ac=0;ac<this.drawables.length;ac++){drawable=this.drawables[ac];this.saved_filters_managers.push(drawable.filters_manager);drawable.filters_manager=this.filters_manager}}this.filters_manager.init_filters()},show_composite_track:function(){var ad=new f(this.view,this.view,{name:this.prefs.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ad,true);ad.request_draw()},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){A.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(A.prototype.to_dict.call(this),{filters:this.filters_manager.to_dict()});if(this.filters_manager.visible()){this.setup_multitrack_filtering()}return ac},request_draw:function(ac){ab.each(this.drawables,function(ad){ad.request_draw(ac)})}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});A.call(this,"View",ac.container,ac);this.chrom=null;this.vis_id=ac.vis_id;this.dbkey=ac.dbkey;this.label_tracks=[];this.tracks_to_be_redrawn=[];this.max_low=0;this.max_high=0;this.zoom_factor=3;this.min_separation=30;this.has_changes=false;this.load_chroms_deferred=null;this.render();this.canvas_manager=new y.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new j({track:this,params:[{key:"a_color",label:"A Color",type:"color",default_value:"#FF0000"},{key:"c_color",label:"C Color",type:"color",default_value:"#00FF00"},{key:"g_color",label:"G Color",type:"color",default_value:"#0000FF"},{key:"t_color",label:"T Color",type:"color",default_value:"#FF00FF"},{key:"n_color",label:"N Color",type:"color",default_value:"#AAAAAA"}],saved_values:ac.prefs,onchange:function(){track.request_redraw({clear_tile_cache:true})}})},render:function(){this.requested_redraw=false;var ae=this.container,ac=this;this.top_container=$("<div/>").addClass("top-container").appendTo(ae);this.browser_content_div=$("<div/>").addClass("content").css("position","relative").appendTo(ae);this.bottom_container=$("<div/>").addClass("bottom-container").appendTo(ae);this.top_labeltrack=$("<div/>").addClass("top-labeltrack").appendTo(this.top_container);this.viewport_container=$("<div/>").addClass("viewport-container").attr("id","viewport-container").appendTo(this.browser_content_div);this.content_div=this.viewport_container;k(this.viewport_container,ac);this.intro_div=$("<div/>").addClass("intro").appendTo(this.viewport_container).hide();var af=$("<div/>").text("Add Datasets to Visualization").addClass("action-button").appendTo(this.intro_div).click(function(){y.select_datasets(galaxy_config.root+"visualization/list_current_history_datasets",galaxy_config.root+"api/datasets",{"f-dbkey":ac.dbkey},function(ag){ab.each(ag,function(ah){ac.add_drawable(p(ah,ac,ac))})})});this.nav_labeltrack=$("<div/>").addClass("nav-labeltrack").appendTo(this.bottom_container);this.nav_container=$("<div/>").addClass("trackster-nav-container").prependTo(this.top_container);this.nav=$("<div/>").addClass("trackster-nav").appendTo(this.nav_container);this.overview=$("<div/>").addClass("overview").appendTo(this.bottom_container);this.overview_viewport=$("<div/>").addClass("overview-viewport").appendTo(this.overview);this.overview_close=$("<a/>").attr("title","Close overview").addClass("icon-button overview-close tooltip").hide().appendTo(this.overview_viewport);this.overview_highlight=$("<div/>").addClass("overview-highlight").hide().appendTo(this.overview_viewport);this.overview_box_background=$("<div/>").addClass("overview-boxback").appendTo(this.overview_viewport);this.overview_box=$("<div/>").addClass("overview-box").appendTo(this.overview_viewport);this.default_overview_height=this.overview_box.height();this.nav_controls=$("<div/>").addClass("nav-controls").appendTo(this.nav);this.chrom_select=$("<select/>").attr({name:"chrom"}).css("width","15em").append("<option value=''>Loading</option>").appendTo(this.nav_controls);var ad=function(ag){if(ag.type==="focusout"||(ag.keyCode||ag.which)===13||(ag.keyCode||ag.which)===27){if((ag.keyCode||ag.which)!==27){ac.go_to($(this).val())}$(this).hide();$(this).val("");ac.location_span.show();ac.chrom_select.show()}};this.nav_input=$("<input/>").addClass("nav-input").hide().bind("keyup focusout",ad).appendTo(this.nav_controls);this.location_span=$("<span/>").addClass("location").attr("original-title","Click to change location").tooltip({placement:"bottom"}).appendTo(this.nav_controls);this.location_span.click(function(){ac.location_span.hide();ac.chrom_select.hide();ac.nav_input.val(ac.chrom+":"+ac.low+"-"+ac.high);ac.nav_input.css("display","inline-block");ac.nav_input.select();ac.nav_input.focus();ac.nav_input.autocomplete({source:function(ai,ag){var aj=[],ah=$.map(ac.get_tracks(d),function(ak){return ak.data_manager.search_features(ai.term).success(function(al){aj=aj.concat(al)})});$.when.apply($,ah).done(function(){ag($.map(aj,function(ak){return{label:ak[0],value:ak[1]}}))})}})});if(this.vis_id!==undefined){this.hidden_input=$("<input/>").attr("type","hidden").val(this.vis_id).appendTo(this.nav_controls)}this.zo_link=$("<a/>").attr("id","zoom-out").attr("title","Zoom out").tooltip({placement:"bottom"}).click(function(){ac.zoom_out();ac.request_redraw()}).appendTo(this.nav_controls);this.zi_link=$("<a/>").attr("id","zoom-in").attr("title","Zoom in").tooltip({placement:"bottom"}).click(function(){ac.zoom_in();ac.request_redraw()}).appendTo(this.nav_controls);this.load_chroms_deferred=this.load_chroms({low:0});this.chrom_select.bind("change",function(){ac.change_chrom(ac.chrom_select.val())});this.browser_content_div.click(function(ag){$(this).find("input").trigger("blur")});this.browser_content_div.bind("dblclick",function(ag){ac.zoom_in(ag.pageX,this.viewport_container)});this.overview_box.bind("dragstart",function(ag,ah){this.current_x=ah.offsetX}).bind("drag",function(ag,ai){var aj=ai.offsetX-this.current_x;this.current_x=ai.offsetX;var ah=Math.round(aj/ac.viewport_container.width()*(ac.max_high-ac.max_low));ac.move_delta(-ah)});this.overview_close.click(function(){ac.reset_overview()});this.viewport_container.bind("draginit",function(ag,ah){if(ag.clientX>ac.viewport_container.width()-16){return false}}).bind("dragstart",function(ag,ah){ah.original_low=ac.low;ah.current_height=ag.clientY;ah.current_x=ah.offsetX}).bind("drag",function(ai,ak){var ag=$(this);var al=ak.offsetX-ak.current_x;var ah=ag.scrollTop()-(ai.clientY-ak.current_height);ag.scrollTop(ah);ak.current_height=ai.clientY;ak.current_x=ak.offsetX;var aj=Math.round(al/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}).bind("mousewheel",function(ai,ak,ah,ag){if(ah){ah*=50;var aj=Math.round(-ah/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}});this.top_labeltrack.bind("dragstart",function(ag,ah){return $("<div />").css({height:ac.browser_content_div.height()+ac.top_labeltrack.height()+ac.nav_labeltrack.height()+1,top:"0px",position:"absolute","background-color":"#ccf",opacity:0.5,"z-index":1000}).appendTo($(this))}).bind("drag",function(ak,al){$(al.proxy).css({left:Math.min(ak.pageX,al.startX)-ac.container.offset().left,width:Math.abs(ak.pageX-al.startX)});var ah=Math.min(ak.pageX,al.startX)-ac.container.offset().left,ag=Math.max(ak.pageX,al.startX)-ac.container.offset().left,aj=(ac.high-ac.low),ai=ac.viewport_container.width();ac.update_location(Math.round(ah/ai*aj)+ac.low,Math.round(ag/ai*aj)+ac.low)}).bind("dragend",function(al,am){var ah=Math.min(al.pageX,am.startX),ag=Math.max(al.pageX,am.startX),aj=(ac.high-ac.low),ai=ac.viewport_container.width(),ak=ac.low;ac.low=Math.round(ah/ai*aj)+ak;ac.high=Math.round(ag/ai*aj)+ak;$(am.proxy).remove();ac.request_redraw()});this.add_label_track(new W(this,{content_div:this.top_labeltrack}));this.add_label_track(new W(this,{content_div:this.nav_labeltrack}));$(window).bind("resize",function(){if(this.resize_timer){clearTimeout(this.resize_timer)}this.resize_timer=setTimeout(function(){ac.resize_window()},500)});$(document).bind("redraw",function(){ac.redraw()});this.reset();$(window).trigger("resize")},get_base_color:function(ac){return this.config.get("values")[ac.toLowerCase()+"_color"]||this.config.get("values").n_color}});q(Y.prototype,A.prototype,{changed:function(){this.has_changes=true},update_intro_div:function(){if(this.drawables.length===0){this.intro_div.show()}else{this.intro_div.hide()}},trigger_navigate:function(ad,af,ac,ag){if(this.timer){clearTimeout(this.timer)}if(ag){var ae=this;this.timer=setTimeout(function(){ae.trigger("navigate",ad+":"+af+"-"+ac)},500)}else{view.trigger("navigate",ad+":"+af+"-"+ac)}},update_location:function(ac,ae){this.location_span.text(commatize(ac)+" - "+commatize(ae));this.nav_input.val(this.chrom+":"+commatize(ac)+"-"+commatize(ae));var ad=view.chrom_select.val();if(ad!==""){this.trigger_navigate(ad,view.low,view.high,true)}},load_chroms:function(ae){ae.num=x;var ac=this,ad=$.Deferred();$.ajax({url:galaxy_config.root+"api/genomes/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){var ah=new D(ac);ac.add_label_track(ah);ac.reference_track=ah}ac.chrom_data=ag.chrom_info;var ak='<option value="">Select Chrom/Contig</option>';for(var aj=0,af=ac.chrom_data.length;aj<af;aj++){var ai=ac.chrom_data[aj].chrom;ak+='<option value="'+ai+'">'+ai+"</option>"}if(ag.prev_chroms){ak+='<option value="previous">Previous '+x+"</option>"}if(ag.next_chroms){ak+='<option value="next">Next '+x+"</option>"}ac.chrom_select.html(ak);ac.chrom_start_index=ag.start_index;ad.resolve(ag.chrom_info)},error:function(){alert("Could not load chroms for this dbkey:",ac.dbkey)}});return ad},change_chrom:function(ah,ad,aj){var ae=this;if(!ae.chrom_data){ae.load_chroms_deferred.then(function(){ae.change_chrom(ah,ad,aj)});return}if(!ah||ah==="None"){return}if(ah==="previous"){ae.load_chroms({low:this.chrom_start_index-x});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+x});return}var ai=$.grep(ae.chrom_data,function(ak,al){return ak.chrom===ah})[0];if(ai===undefined){ae.load_chroms({chrom:ah},function(){ae.change_chrom(ah,ad,aj)});return}else{if(ah!==ae.chrom){ae.chrom=ah;ae.chrom_select.val(ae.chrom);ae.max_high=ai.len-1;ae.reset();for(var ag=0,ac=ae.drawables.length;ag<ac;ag++){var af=ae.drawables[ag];if(af.init){af.init()}}if(ae.reference_track){ae.reference_track.init()}}if(ad&&aj){ae.low=Math.max(ad,0);ae.high=Math.min(aj,ae.max_high)}else{ae.low=0;ae.high=ae.max_high}ae.reset_overview();ae.request_redraw()}},go_to:function(ag){ag=ag.replace(/,/g,"");ag=ag.replace(/:|\-/g," ");var ad=ag.split(/\s+/),af=ad[0],ae=(ad[1]?parseInt(ad[1],10):null),ac=(ad[2]?parseInt(ad[2],10):null);if(!ac){ae=ae-15;ac=ae+15}this.change_chrom(af,ae,ac)},move_fraction:function(ae){var ac=this;var ad=ac.high-ac.low;this.move_delta(ae*ad)},move_delta:function(af){var ac=this;var ae=ac.high-ac.low;if(ac.low-af<ac.max_low){ac.low=ac.max_low;ac.high=ac.max_low+ae}else{if(ac.high-af>ac.max_high){ac.high=ac.max_high;ac.low=ac.max_high-ae}else{ac.high-=af;ac.low-=af}}ac.request_redraw({data_fetch:false});if(this.redraw_on_move_fn){clearTimeout(this.redraw_on_move_fn)}this.redraw_on_move_fn=setTimeout(function(){ac.request_redraw()},200);var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);ac.init();this.changed();this.update_intro_div()},add_label_track:function(ac){ac.view=this;ac.init();this.label_tracks.push(ac)},remove_drawable:function(ae,ad){A.prototype.remove_drawable.call(this,ae);if(ad){var ac=this;ae.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})}},reset:function(){this.low=this.max_low;this.high=this.max_high;this.viewport_container.find(".yaxislabel").remove()},request_redraw:function(ad,ae){var ac=this,af=(ae?[ae]:ac.drawables);ab.each(af,function(ag){var ah=ab.find(ac.tracks_to_be_redrawn,function(ai){return ai[0]===ag});if(ah){ah[1]=ad}else{ac.tracks_to_be_redrawn.push([ag,ad])}});if(!this.requested_redraw){requestAnimationFrame(function(){ac._redraw()});this.requested_redraw=true}},_redraw:function(){this.requested_redraw=false;var ac=this.low,ag=this.high;if(ac<this.max_low){ac=this.max_low}if(ag>this.max_high){ag=this.max_high}var ad=this.high-this.low;if(this.high!==0&&ad<this.min_separation){ag=ac+this.min_separation}this.low=Math.floor(ac);this.high=Math.ceil(ag);this.update_location(this.low,this.high);this.resolution_px_b=this.viewport_container.width()/(this.high-this.low);var af=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ah=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ae=13;this.overview_box.css({left:af,width:Math.max(ae,ah)}).show();if(ah<ae){this.overview_box.css("left",af-(ae-ah)/2)}if(this.overview_highlight){this.overview_highlight.css({left:af,width:ah})}ab.each(this.tracks_to_be_redrawn,function(ak){var ai=ak[0],aj=ak[1];if(ai){ai._draw(aj)}});this.tracks_to_be_redrawn=[];ab.each(this.label_tracks,function(ai){ai._draw()})},zoom_in:function(ad,ae){if(this.max_high===0||this.high-this.low<=this.min_separation){return}var af=this.high-this.low,ag=af/2+this.low,ac=(af/this.zoom_factor)/2;if(ad){ag=ad/this.viewport_container.width()*(this.high-this.low)+this.low}this.low=Math.round(ag-ac);this.high=Math.round(ag+ac);this.changed();this.request_redraw()},zoom_out:function(){if(this.max_high===0){return}var ad=this.high-this.low,ae=ad/2+this.low,ac=(ad*this.zoom_factor)/2;this.low=Math.round(ae-ac);this.high=Math.round(ae+ac);this.changed();this.request_redraw()},resize_window:function(){this.viewport_container.height(this.container.height()-this.top_container.height()-this.bottom_container.height());this.request_redraw()},set_overview:function(ae){if(this.overview_drawable){if(this.overview_drawable.dataset.id===ae.dataset.id){return}this.overview_viewport.find(".track").remove()}var ad=ae.copy({content_div:this.overview_viewport}),ac=this;ad.header_div.hide();ad.is_overview=true;ac.overview_drawable=ad;this.overview_drawable.postdraw_actions=function(){ac.overview_highlight.show().height(ac.overview_drawable.content_div.height());ac.overview_viewport.height(ac.overview_drawable.content_div.height()+ac.overview_box.outerHeight());ac.overview_close.show();ac.resize_window()};ac.overview_drawable.request_draw();this.changed()},reset_overview:function(){$(".tooltip").remove();this.overview_viewport.find(".track-tile").remove();this.overview_viewport.height(this.default_overview_height);this.overview_box.height(this.default_overview_height);this.overview_close.hide();this.overview_highlight.hide();view.resize_window();view.overview_drawable=null}});var s=R.Tool.extend({defaults:{track:null},initialize:function(ac){if(ac.tool_state!==undefined){this.set("hidden",ac.tool_state.hidden)}this.remove_inputs(["data","hidden_data","conditional"])},state_dict:function(ac){return ab.extend(this.get_inputs_dict(),{hidden:!this.is_visible()})}});var v=Backbone.View.extend({events:{"change input":"update_value"},render:function(){var ae=this.$el.addClass("param-row"),af=this.model;var ac=$("<div>").addClass("param-label").text(af.get("label")).appendTo(ae);var ad=$("<div/>").addClass("param-input").html(af.get("html")).appendTo(ae);ad.find(":input").val(af.get("value"));$("<div style='clear: both;'/>").appendTo(ae)},update_value:function(ac){this.model.set_value($(ac.target).val())}});var aa=Backbone.View.extend({initialize:function(ac){this.model.on("change:hidden",this.set_visible,this)},render:function(){var ad=this;tool=this.model,parent_div=this.$el.addClass("dynamic-tool").hide();parent_div.bind("drag",function(ah){ah.stopPropagation()}).click(function(ah){ah.stopPropagation()}).bind("dblclick",function(ah){ah.stopPropagation()}).keydown(function(ah){ah.stopPropagation()});var ae=$("<div class='tool-name'>").appendTo(parent_div).text(tool.get("name"));tool.get("inputs").each(function(ai){var ah=new v({model:ai});ah.render();parent_div.append(ah.$el)});parent_div.find("input").click(function(){$(this).select()});var af=$("<div>").addClass("param-row").appendTo(parent_div);var ag=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(af);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(af);ac.click(function(){ad.run_on_region()});ag.click(function(){ad.run_on_dataset()});if(tool.is_visible()){this.$el.show()}},set_visible:function(){if(this.model.is_visible()){this.$el.show()}else{this.$el.hide()}},update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},run_on_dataset:function(){var ac=this.model;this.run({target_dataset_id:this.model.get("track").dataset.id,action:"rerun",tool_id:ac.id},null,function(ad){Galaxy.modal.show({title:ac.get("name")+" is Running",body:ac.get("name")+" is running on the complete dataset. Tool outputs are in dataset's history.",buttons:{Close:function(){Galaxy.modal.hide()}}})})},run_on_region:function(){var ad=this.model.get("track"),ag=this.model,ai=new y.GenomeRegion({chrom:ad.view.chrom,start:ad.view.low,end:ad.view.high}),aj={target_dataset_id:ad.dataset.id,action:"rerun",tool_id:ag.id,regions:[ai.toJSON()]},ah=ad,al=aj.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ak=new P(view,view,{name:this.prefs.name});var af=ah.container.replace_drawable(ah,ak,false);ak.container_div.insertBefore(ah.view.content_div.children()[af]);ak.add_drawable(ah);ah.container_div.appendTo(ak.content_div);ac=ak}else{ac=ah.container}var ae=new ah.constructor(view,ac,{name:al,hda_ldda:"hda"});ae.init_for_tool_data();ae.change_mode(ah.mode);ae.set_filters_manager(ah.filters_manager.copy(ae));ae.update_icons();ac.add_drawable(ae);ae.tiles_div.text("Starting job.");this.run(aj,ae,function(am){ae.set_dataset(new X.Dataset(am));ae.tiles_div.text("Running job.");ae.init()})},run:function(ac,ae,af){ac.inputs=this.model.get_inputs_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_config.root+"api/tools",data:JSON.stringify(ac),dataType:"json",contentType:"application/json",type:"POST"},interval:2000,success_fn:function(ag){return ag!=="pending"}});$.when(ad.go()).then(function(ag){if(ag==="no converter"){ae.container_div.addClass("error");ae.content_div.text(J)}else{if(ag.error){ae.container_div.addClass("error");ae.content_div.text(z+ag.message)}else{af(ag)}}})}});var E=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};E.prototype.gen_val=function(ac){if(this.filter.high===Number.MAX_VALUE||this.filter.low===-Number.MAX_VALUE||this.filter.low===this.filter.high){return this.default_val}return((parseFloat(ac[this.filter.index])-this.filter.low)/(this.filter.high-this.filter.low))};var j=Backbone.Model.extend({initialize:function(ad){var ac={};ab.each(ad.params,function(ae){ac[ae.key]=ae.default_value});if(ad.saved_values){ab.each(this.get("params"),function(ae){if(ae.key in ad.saved_values){ac[ae.key]=ad.saved_values[ae.key]}})}this.set("values",ac)},set_param_default_value:function(ad,ac){var ae=ab.find(this.get("params"),function(af){return af.key===ad});if(ae){ae.default_value=ac}},set_param_value:function(ac,ad){var ae=ab.find(this.get("params"),function(af){return af.key===ac});if(ae){if(typeof ad==="string"||ad instanceof String){if(ad.trim()===""){ad=ae.default_value}else{if(ae.type==="float"){ad=parseFloat(ad)}else{if(ae.type==="int"){ad=parseInt(ad,10)}}}}}if(this.get("values")[ac]!==ad){this.get("values")[ac]=ad;this.trigger("change:values");return true}else{return false}}});var a=Backbone.View.extend({render:function(){var aj=this.model;var ac=$("<div/>").keydown(function(ak){ak.stopPropagation()});var ai;function ah(ao,ak){for(var at=0;at<ao.length;at++){ai=ao[at];if(ai.hidden){continue}var am="param_"+at;var ax=aj.get("values")[ai.key];var az=$("<div class='form-row' />").appendTo(ak);az.append($("<label />").attr("for",am).text(ai.label+":"));if(ai.type==="bool"){az.append($('<input type="checkbox" />').attr("id",am).attr("name",am).attr("checked",ax))}else{if(ai.type==="text"){az.append($('<input type="text"/>').attr("id",am).val(ax).click(function(){$(this).select()}))}else{if(ai.type==="select"){var av=$("<select />").attr("id",am);for(var aq=0;aq<ai.options.length;aq++){$("<option/>").text(ai.options[aq].label).attr("value",ai.options[aq].value).appendTo(av)}av.val(ax);az.append(av)}else{if(ai.type==="color"){var ay=$("<div/>").appendTo(az),au=$("<input />").attr("id",am).attr("name",am).val(ax).css("float","left").appendTo(ay).click(function(aB){$(".tooltip").removeClass("in");var aA=$(this).siblings(".tooltip").addClass("in");aA.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top+Galaxy.modal.scrollTop()-($(aA).height()/2)+($(this).height()/2)}).show();aA.click(function(aC){aC.stopPropagation()});$(document).bind("click.color-picker",function(){aA.hide();$(document).unbind("click.color-picker")});aB.stopPropagation()}),ar=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(ay).attr("title","Set new random color").tooltip(),aw=$("<div class='tooltip right' style='position: absolute;' />").appendTo(ay).hide(),an=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(aw),al=$("<div class='tooltip-arrow'></div>").appendTo(aw),ap=$.farbtastic(an,{width:100,height:100,callback:au,color:ax});ay.append($("<div/>").css("clear","both"));(function(aA){ar.click(function(){aA.setColor(l.get_random_color())})})(ap)}else{az.append($("<input />").attr("id",am).attr("name",am).val(ax))}}}}if(ai.help){az.append($("<div class='help'/>").text(ai.help))}}}ah(aj.get("params"),ac);var ad=this,ag=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ae=function(){ad.update_from_form($(Galaxy.modal.el));Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},af=function(ak){if((ak.keyCode||ak.which)===27){ag()}else{if((ak.keyCode||ak.which)===13){ae()}}};$(window).bind("keypress.check_enter_esc",af);Galaxy.modal.show({title:"Configure",body:ac,buttons:{Cancel:ag,Ok:ae}})},update_from_form:function(ac){var ad=this.model;var ae=false;ab.each(ad.get("params"),function(ah,af){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}ae=ad.set_param_value(ah.key,ag)||ae}})}});var c=function(ac,af,ag,ad,ae){this.track=ac;this.region=af;this.low=af.get("start");this.high=af.get("end");this.w_scale=ag;this.canvas=ad;this.html_elt=$("<div class='track-tile'/>").append(ad);this.data=ae;this.stale=false};c.prototype.predisplay_actions=function(){};var M=function(ac,af,ag,ad,ae){c.call(this,ac,af,ag,ad,ae)};M.prototype.predisplay_actions=function(){};var O=function(af,am,ao,ae,ah,ai,ap,ad,al){c.call(this,af,am,ao,ae,ah);this.mode=ai;this.all_slotted=ad;this.feature_mapper=al;this.has_icons=false;if(ap){this.has_icons=true;var aj=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:F,width:ae.width}).prependTo(this.html_elt);var ak=new y.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),an=ah.length,ag=$("<a/>").addClass("icon more-down").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a/>").addClass("icon more-across").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ag.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.DEEP_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()});ac.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.BROAD_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()})}};q(O.prototype,c.prototype);O.prototype.predisplay_actions=function(){var ad=this,ac={};if(ad.mode!=="Pack"){return}$(this.html_elt).hover(function(){this.hovered=true;$(this).mousemove()},function(){this.hovered=false;$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()}).mousemove(function(ao){if(!this.hovered){return}var aj=$(this).offset(),an=ao.pageX-aj.left,am=ao.pageY-aj.top,at=ad.feature_mapper.get_feature_data(an,am),ak=(at?at[0]:null);$(this).parents(".track-content").children(".overlay").children(".feature-popup").each(function(){if(!ak||$(this).attr("id")!==ak.toString()){$(this).remove()}});if(at){var af=ac[ak];if(!af){var ap={name:at[3],start:at[1],end:at[2],strand:at[4]},ai=ad.track.filters_manager.filters,ah;for(var al=0;al<ai.length;al++){ah=ai[al];ap[ah.name]=at[ah.index]}af=$("<div/>").attr("id",ak).addClass("feature-popup");var au=$("<table/>"),ar,aq,av;for(ar in ap){aq=ap[ar];av=$("<tr/>").appendTo(au);$("<th/>").appendTo(av).text(ar);$("<td/>").attr("align","left").appendTo(av).text(typeof(aq)==="number"?V(aq,2):aq)}af.append($("<div class='feature-popup-inner'>").append(au));ac[ak]=af}af.appendTo($(this).parents(".track-content").children(".overlay"));var ag=an+parseInt(ad.html_elt.css("left"),10)-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"),10)+7;af.css("left",ag+"px").css("top",ae+"px")}else{if(!ao.isPropagationStopped()){ao.stopPropagation();$(this).siblings().each(function(){$(this).trigger(ao)})}}}).mouseleave(function(){$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()})};var g=function(ad,ac,ae){q(ae,{drag_handle_class:"draghandle"});r.call(this,ad,ac,ae);this.dataset=null;if(ae.dataset){this.dataset=(ae.dataset instanceof Backbone.Model?ae.dataset:X.Dataset.findOrCreate(ae.dataset))}this.dataset_check_type="converted_datasets_state";this.data_url_extra_params={};this.data_query_wait=("data_query_wait" in ae?ae.data_query_wait:K);this.data_manager=("data_manager" in ae?ae.data_manager:new y.GenomeDataManager({dataset:this.dataset,genome:new y.Genome({key:ad.dbkey,chroms_info:{chrom_info:ad.chrom_data}}),data_mode_compatible:this.data_and_mode_compatible,can_subset:this.can_subset}));this.min_height_px=16;this.max_height_px=800;this.visible_height_px=this.prefs.height;this.content_div=$("<div class='track-content'>").appendTo(this.container_div);if(this.container){this.container.content_div.append(this.container_div);if(!("resize" in ae)||ae.resize){this.add_resize_handle()}}};q(g.prototype,r.prototype,{action_icons_def:[{name:"mode_icon",title:"Set display mode",css_class:"chevron-expand",on_click_fn:function(){}},r.prototype.action_icons_def[0],{name:"overview_icon",title:"Set as overview",css_class:"overview-icon",on_click_fn:function(ac){ac.view.set_overview(ac)}},r.prototype.action_icons_def[1],{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters()}else{ac.filters_manager.init_filters()}ac.filters_manager.toggle()}},{name:"tools_icon",title:"Tool",css_class:"hammer",on_click_fn:function(ac){ac.tool.toggle();if(ac.tool.is_visible()){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".tooltip").remove()}},{name:"param_space_viz_icon",title:"Tool parameter space visualization",css_class:"arrow-split",on_click_fn:function(ac){var af='<strong>Tool</strong>: <%= track.tool.name %><br/><strong>Dataset</strong>: <%= track.name %><br/><strong>Region(s)</strong>: <select name="regions"><option value="cur">current viewing area</option><option value="bookmarks">bookmarks</option><option value="both">current viewing area and bookmarks</option></select>',ae=ab.template(af,{track:ac});var ah=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new y.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new y.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}Galaxy.modal.hide();window.location.href=galaxy_config.root+"visualization/sweepster?"+$.param({dataset_id:ac.dataset.id,hda_ldda:ac.dataset.get("hda_ldda"),regions:JSON.stringify(new Backbone.Collection(al).toJSON())})},ag=function(ai){if((ai.keyCode||ai.which)===27){ah()}else{if((ai.keyCode||ai.which)===13){ad()}}};Galaxy.modal.show({title:"Visualize tool parameter space and output from different parameter settings?",body:ae,buttons:{No:ah,Yes:ad}})}},r.prototype.action_icons_def[2]],can_draw:function(){return this.dataset&&r.prototype.can_draw.call(this)},build_container_div:function(){return $("<div/>").addClass("track").attr("id","track_"+this.id).css("position","relative")},build_header_div:function(){var ac=$("<div class='track-header'/>");if(this.view.editor){this.drag_div=$("<div/>").addClass(this.drag_handle_class).appendTo(ac)}this.name_div=$("<div/>").addClass("track-name").appendTo(ac).text(this.prefs.name).attr("id",this.prefs.name.replace(/\s+/g,"-").replace(/[^a-zA-Z0-9\-]/g,"").toLowerCase());return ac},set_dataset:function(ac){this.dataset=ac;this.data_manager.set("dataset",ac)},on_resize:function(){this.request_draw({clear_tile_cache:true})},add_resize_handle:function(){var ac=this;var af=false;var ae=false;var ad=$("<div class='track-resize'>");$(ac.container_div).hover(function(){if(ac.prefs.content_visible){af=true;ad.show()}},function(){af=false;if(!ae){ad.hide()}});ad.hide().bind("dragstart",function(ag,ah){ae=true;ah.original_height=$(ac.content_div).height()}).bind("drag",function(ah,ai){var ag=Math.min(Math.max(ai.original_height+ai.deltaY,ac.min_height_px),ac.max_height_px);$(ac.tiles_div).css("height",ag);ac.visible_height_px=(ac.max_height_px===ag?0:ag);ac.on_resize()}).bind("dragend",function(ag,ah){ac.tile_cache.clear();ae=false;if(!af){ad.hide()}ac.config.get("values").height=ac.visible_height_px;ac.changed()}).appendTo(ac.container_div)},set_display_modes:function(af,ai){this.display_modes=af;this.mode=(ai?ai:(this.config&&this.config.get("values").mode?this.config.get("values").mode:this.display_modes[0]));this.action_icons.mode_icon.attr("title","Set display mode (now: "+this.mode+")");var ad=this,ag={};for(var ae=0,ac=ad.display_modes.length;ae<ac;ae++){var ah=ad.display_modes[ae];ag[ah]=function(aj){return function(){ad.change_mode(aj);ad.icons_div.show();ad.container_div.mouseleave(function(){ad.icons_div.hide()})}}(ah)}make_popupmenu(this.action_icons.mode_icon,ag)},build_action_icons:function(){r.prototype.build_action_icons.call(this,this.action_icons_def);if(this.display_modes!==undefined){this.set_display_modes(this.display_modes)}},hide_contents:function(){this.tiles_div.hide();this.container_div.find(".yaxislabel, .track-resize").hide()},show_contents:function(){this.tiles_div.show();this.container_div.find(".yaxislabel, .track-resize").show();this.request_draw()},get_type:function(){if(this instanceof W){return"LabelTrack"}else{if(this instanceof D){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof T){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof d){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.tiles_div.css("height","auto");ad.tiles_div.text("").children().remove();ad.container_div.removeClass("nodata error pending");if(!ad.dataset.id){return}var ac=$.Deferred(),af={hda_ldda:ad.dataset.get("hda_ldda"),data_type:this.dataset_check_type,chrom:ad.view.chrom,retry:ae};$.getJSON(this.dataset.url(),af,function(ag){if(!ag||ag==="error"||ag.kind==="error"){ad.container_div.addClass("error");ad.tiles_div.text(o);if(ag.message){ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("View error").click(function(){Galaxy.modal.show({title:"Trackster Error",body:"<pre>"+ag.message+"</pre>",buttons:{Close:function(){Galaxy.modal.hide()}}})}));ad.tiles_div.append($("<span/>").text(" "));ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("Try again").click(function(){ad.init(true)}))}}else{if(ag==="no converter"){ad.container_div.addClass("error");ad.tiles_div.text(J)}else{if(ag==="no data"||(ag.data!==undefined&&(ag.data===null||ag.data.length===0))){ad.container_div.addClass("nodata");ad.tiles_div.text(G)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(w);setTimeout(function(){ad.init()},ad.data_query_wait)}else{if(ag==="data"||ag.status==="data"){if(ag.valid_chroms){ad.valid_chroms=ag.valid_chroms;ad.update_icons()}ad.tiles_div.text(U);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when.apply($,ad.predraw_init()).done(function(){ac.resolve();ad.container_div.removeClass("nodata error pending");ad.request_draw()})}else{ac.resolve()}}}}}}});this.update_icons();return ac},predraw_init:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){ac.container_div.addClass("line-track");var af=ad.data;if(af&&af.min&&af.max){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.config.set_param_default_value("min_value",ae);ac.config.set_param_default_value("max_value",ag);ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},get_drawables:function(){return this}});var N=function(ae,ad,ag){g.call(this,ae,ad,ag);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in ag?ag.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=(ag.tool?new s(ab.extend(ag.tool,{track:this,tool_state:ag.tool_state})):null);this.tile_cache=new y.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){var af=new aa({model:this.tool});af.render();this.dynamic_tool_div=af.$el;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);if(!this.prefs.content_visible){this.tiles_div.hide()}this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(ag.mode){this.change_mode(ag.mode)}};q(N.prototype,r.prototype,g.prototype,{action_icons_def:g.prototype.action_icons_def.concat([{name:"show_more_rows_icon",title:"To minimize track height, not all feature rows are displayed. Click to display more rows.",css_class:"exclamation",on_click_fn:function(ac){$(".tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw({clear_tile_cache:true})},hide:true}]),copy:function(ac){var ad=this.to_dict();q(ad,{data_manager:this.data_manager});var ae=new this.constructor(this.view,ac,ad);ae.change_mode(this.mode);ae.enabled=this.enabled;return ae},set_filters_manager:function(ac){this.filters_manager=ac;this.header_div.after(this.filters_manager.parent_div)},to_dict:function(){return{track_type:this.get_type(),dataset:{id:this.dataset.id,hda_ldda:this.dataset.get("hda_ldda")},prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},set_min_max:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){var af=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.get("values").mode=ad;if(ad==="Auto"){this.data_manager.clear()}ac.request_draw({clear_tile_cache:true});this.action_icons.mode_icon.attr("title","Set display mode (now: "+ac.mode+")");return ac},update_icons:function(){var ac=this;if(ac.filters_available){ac.action_icons.filters_icon.show()}else{ac.action_icons.filters_icon.hide()}if(ac.tool){ac.action_icons.tools_icon.show();ac.action_icons.param_space_viz_icon.show()}else{ac.action_icons.tools_icon.hide();ac.action_icons.param_space_viz_icon.hide()}},_gen_tile_cache_key:function(ad,ac){return ad+"_"+ac},request_draw:function(ac){if(ac&&ac.clear_tile_cache){this.tile_cache.clear()}this.view.request_redraw(ac,this)},before_draw:function(){this.max_height_px=0},_draw:function(aq){if(!this.can_draw()){return}var an=aq&&aq.clear_after,al=this.view.low,ag=this.view.high,aj=ag-al,ad=this.view.container.width(),ap=this.view.resolution_px_b,af=1/ap;if(this.is_overview){al=this.view.max_low;ag=this.view.max_high;ap=ad/(view.max_high-view.max_low);af=1/ap}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(af*S)),ak,am,ah,ai=[],ao=[];while((ac*S*af)<ag){ak=Math.floor(ac*S*af);am=new y.GenomeRegion({chrom:this.view.chrom,start:ak,end:Math.min(ak+Math.ceil(S*af),this.view.max_high)});ah=this.draw_helper(am,ap,aq);ai.push(ah);$.when(ah).then(function(ar){ao.push(ar)});ac+=1}if(!an){this.tiles_div.children(".remove").removeClass("remove").remove()}var ae=this;$.when.apply($,ai).then(function(){ae.tiles_div.children(".remove").remove();ao=ab.filter(ao,function(ar){return ar!==null});if(ao.length!==0){ae.postdraw_actions(ao,ad,ap,an)}})},_add_yaxis_label:function(af,ah){var ad=this,ag=(af==="max"?"top":"bottom"),ai=(af==="max"?"max":"min"),ac=(af==="max"?"max_value":"min_value"),ae=this.container_div.find(".yaxislabel."+ag);ah=ah||function(){ad.request_draw({clear_tile_cache:true})};if(ae.length!==0){ae.text(ad.prefs[ac])}else{ae=$("<div/>").text(ad.prefs[ac]).make_text_editable({num_cols:12,on_finish:function(aj){$(".tooltip").remove();ad.config.set_param_value(ac,aj);ah()},help_text:"Set "+ai+" value"}).addClass("yaxislabel "+ag).css("color",this.prefs.label_color);this.container_div.prepend(ae)}},postdraw_actions:function(af,ag,ai,ac){var ae=ab.filter(af,function(aj){return(aj instanceof M)});if(ae.length>0){this.max_height_px=0;var ad=this;ab.each(af,function(aj){if(!(aj instanceof M)){aj.html_elt.remove();ad.draw_helper(aj.region,ai,{force:true,mode:"Coverage"})}});ad._add_yaxis_label("max")}else{this.container_div.find(".yaxislabel").remove();var ah=ab.find(af,function(aj){return aj.has_icons});if(ah){ab.each(af,function(aj){if(!aj.has_icons){aj.html_elt.css("padding-top",F)}})}}},get_mode:function(ac){return this.mode},update_auto_mode:function(ac){},_get_drawables:function(){return[this]},draw_helper:function(al,an,ao){if(!ao){ao={}}var ad=ao.force,ai=ao.mode||this.mode,af=1/an,ae=this,ag=this._get_drawables(),am=this._gen_tile_cache_key(an,al),ah=function(ap){return(ap&&"track" in ap)};var aj=(ad?undefined:ae.tile_cache.get_elt(am));if(aj){if(ah(aj)){ae.show_tile(aj,an)}return aj}if(ao.data_fetch===false){return null}var ak=function(){var ap=(ab.find(C,function(ar){return ar===ai})?"Coverage":ai);var aq=ab.map(ag,function(ar){return ar.data_manager.get_data(al,ap,af,ae.data_url_extra_params)});if(view.reference_track){aq.push(view.reference_track.data_manager.get_data(al,ai,af,view.reference_track.data_url_extra_params))}return aq};var ac=$.Deferred();ae.tile_cache.set_elt(am,ac);$.when.apply($,ak()).then(function(){var ap=ak(),av=ap,aB;if(view.reference_track){aB=view.reference_track.data_manager.subset_entry(ap.pop(),al)}var aw=[],at=[];ab.each(ag,function(aG,aD){var aF=aG.mode,aE=av[aD];if(aF==="Auto"){aF=aG.get_mode(aE);aG.update_auto_mode(aF)}aw.push(aF);at.push(aG.get_canvas_height(aE,aF,an,aq))});var au=ae.view.canvas_manager.new_canvas(),ax=al.get("start"),aC=al.get("end"),ar=0,aq=Math.ceil((aC-ax)*an)+ae.left_offset,az=ab.max(at),ay;au.width=aq;au.height=(ao.height||az);var aA=au.getContext("2d");aA.translate(ae.left_offset,0);if(ag.length>1){aA.globalAlpha=0.5;aA.globalCompositeOperation="source-over"}ab.each(ag,function(aE,aD){ay=aE.draw_tile(av[aD],aA,aw[aD],al,an,aB)});if(ay!==undefined){ae.tile_cache.set_elt(am,ay);ae.show_tile(ay,an)}ac.resolve(ay)});return ac},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_line_track_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.LinePainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new M(this,ag,ai,af,ac.data)},draw_tile:function(ac,ad,ag,af,ah,ae){},show_tile:function(ae,ah){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ah;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{this.tiles_div.append(ac)}this.max_height_px=Math.max(this.max_height_px,$(ae.canvas).height());ac.parent().children().css("height",this.max_height_px+"px");var af=this.max_height_px;if(this.visible_height_px!==0){af=Math.min(this.max_height_px,this.visible_height_px)}this.tiles_div.css("height",af+"px")},tool_region_and_parameters_str:function(af){var ac=this,ae=(af!==undefined?af.toString():"all"),ad=ab.values(ac.tool.get_inputs_dict()).join(", ");return" - region=["+ae+"], parameters=["+ad+"]"},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="bigwig"}else{if(ac.dataset_type==="bigwig"||ac.extra_info==="no_detail"){return false}else{return true}}}},can_subset:function(ac){if(ac.message||ac.extra_info==="no_detail"){return false}else{if(ac.dataset_type==="bigwig"){return(ac.data[1][0]-ac.data[0][0]===1)}}return true},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state"}});var W=function(ad,ac){var ae={resize:false};g.call(this,ad,ac,ae);this.container_div.addClass("label-track")};q(W.prototype,g.prototype,{build_header_div:function(){},init:function(){this.enabled=true},predraw_init:function(){},_draw:function(ag){var ae=this.view,af=ae.high-ae.low,aj=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/aj)*aj,ah=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ai=(ac-ae.low)/af*ah;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ai-1}));ac+=aj}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){N.call(this,ad,ac,ag);this.drawables=[];if("drawables" in ag){var af;for(var ae=0;ae<ag.drawables.length;ae++){af=ag.drawables[ae];this.drawables[ae]=p(af,ad,null);if(af.left_offset>this.left_offset){this.left_offset=af.left_offset}}this.enabled=true}ab.each(this.drawables,function(ah){if(ah instanceof d||ah instanceof T){ah.change_mode("Coverage")}});this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,N.prototype,{display_modes:C,action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_group()}}].concat(N.prototype.action_icons_def),to_dict:A.prototype.to_dict,add_drawable:A.prototype.add_drawable,unpack_drawables:A.prototype.unpack_drawables,change_mode:function(ac){N.prototype.change_mode.call(this,ac);for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].change_mode(ac)}},init:function(){var ae=[];for(var ad=0;ad<this.drawables.length;ad++){ae.push(this.drawables[ad].init())}var ac=this;$.when.apply($,ae).then(function(){ac.enabled=true;ac.request_draw()})},update_icons:function(){this.action_icons.filters_icon.hide();this.action_icons.tools_icon.hide();this.action_icons.param_space_viz_icon.hide()},can_draw:r.prototype.can_draw,_get_drawables:function(){return this.drawables},show_group:function(){var af=new P(this.view,this.container,{name:this.prefs.name}),ac;for(var ae=0;ae<this.drawables.length;ae++){ac=this.drawables[ae];ac.update_icons();af.add_drawable(ac);ac.container=af;af.content_div.append(ac.container_div)}var ad=this.container.replace_drawable(this,af,true);af.request_draw({clear_tile_cache:true})},before_draw:function(){N.prototype.before_draw.call(this);var ad=ab.min(ab.map(this.drawables,function(ae){return ae.prefs.min_value})),ac=ab.max(ab.map(this.drawables,function(ae){return ae.prefs.max_value}));this.prefs.min_value=ad;this.prefs.max_value=ac;ab.each(this.drawables,function(ae){ae.prefs.min_value=ad;ae.prefs.max_value=ac})},update_all_min_max:function(){var ac=this;ab.each(this.drawables,function(ad){ad.prefs.min_value=ac.prefs.min_value;ad.prefs.max_value=ac.prefs.max_value});this.request_draw({clear_tile_cache:true})},postdraw_actions:function(ai,ac,al,ah){N.prototype.postdraw_actions.call(this,ai,ac,al,ah);var ag=-1,ae;for(ae=0;ae<ai.length;ae++){var aj=ai[ae].html_elt.find("canvas").height();if(aj>ag){ag=aj}}for(ae=0;ae<ai.length;ae++){var af=ai[ae];if(af.html_elt.find("canvas").height()!==ag){this.draw_helper(af.region,al,{force:true,height:ag});af.html_elt.remove()}}var ad=this,ak=function(){ad.update_all_min_max()};this._add_yaxis_label("min",ak);this._add_yaxis_label("max",ak)}});var D=function(ac){N.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});this.left_offset=ac.canvas_manager.char_width_px;this.container_div.addClass("reference-track");this.data_url=galaxy_config.root+"api/genomes/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new y.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(D.prototype,r.prototype,N.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"height",type:"int",default_value:13,hidden:true}]),build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},predraw_init:function(){},can_draw:r.prototype.can_draw,draw_helper:function(ad,ae,ac){if(ae>this.view.canvas_manager.char_width_px){this.tiles_div.show();return N.prototype.draw_helper.call(this,ad,ae,ac)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(ae,ak,af,ah,al){var ad=this.data_manager.subset_entry(ae,ah),aj=ad.data;var ac=ak.canvas;ak.font=ak.canvas.manager.default_font;ak.textAlign="center";for(var ag=0,ai=aj.length;ag<ai;ag++){ak.fillStyle=this.view.get_base_color(aj[ag]);ak.fillText(aj[ag],Math.floor(ag*al),10)}return new c(this,ah,al,ac,ad)}});var h=function(ad,ac,ae){this.mode="Histogram";N.call(this,ad,ac,ae)};q(h.prototype,r.prototype,N.prototype,{display_modes:C,config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Color",type:"color",default_value:l.get_random_color()},{key:"min_value",label:"Min Value",type:"float",default_value:undefined},{key:"max_value",label:"Max Value",type:"float",default_value:undefined},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:30,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},before_draw:function(){},draw_tile:function(ac,ad,af,ae,ag){return this._draw_line_track_tile(ac,ad,af,ae,ag)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)},postdraw_actions:function(ad,ae,af,ac){this._add_yaxis_label("max");this._add_yaxis_label("min")}});var t=function(ad,ac,ae){this.mode="Heatmap";N.call(this,ad,ac,ae)};q(t.prototype,r.prototype,N.prototype,{display_modes:["Heatmap"],config_params:ab.union(r.prototype.config_params,[{key:"pos_color",label:"Positive Color",type:"color",default_value:"#FF8C00"},{key:"neg_color",label:"Negative Color",type:"color",default_value:"#4169E1"},{key:"min_value",label:"Min Value",type:"float",default_value:-1},{key:"max_value",label:"Max Value",type:"float",default_value:1},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:500,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new c(this,ag,ai,af,ac.data)}});var d=function(ad,ac,ae){N.call(this,ad,ac,ae);this.container_div.addClass("feature-track");this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(d.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true,help:"Show the number of items in each bin when drawing summary histogram"},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"connector_style",label:"Connector style",type:"select",default_value:"fishbones",options:[{label:"Line with arrows",value:"fishbone"},{label:"Arcs",value:"arcs"}]},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.set_painter_from_config();this.request_draw({clear_tile_cache:true})},set_painter_from_config:function(){if(this.config.get("values").connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},postdraw_actions:function(am,ae,an,al){N.prototype.postdraw_actions.call(this,am,ae,an,al);var ag=this,ah;if(ag.filters_manager){var af=ag.filters_manager.filters,aj;for(aj=0;aj<af.length;aj++){af[aj].update_ui_elt()}var ai=false,ak,ad;for(ah=0;ah<am.length;ah++){if(am[ah].data.length){ak=am[ah].data[0];for(aj=0;aj<af.length;aj++){ad=af[aj];if(ad.applies_to(ak)&&ad.min!==ad.max){ai=true;break}}}}if(ag.filters_available!==ai){ag.filters_available=ai;if(!ag.filters_available){ag.filters_manager.hide()}ag.update_icons()}}if(am[0] instanceof O){var ac=true;for(ah=0;ah<am.length;ah++){if(!am[ah].all_slotted){ac=false;break}}if(!ac){this.action_icons.show_more_rows_icon.show()}else{this.action_icons.show_more_rows_icon.hide()}}else{this.action_icons.show_more_rows_icon.hide()}},update_auto_mode:function(ac){if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}this.action_icons.mode_icon.attr("title","Set display mode (now: Auto/"+ac+")")}},incremental_slots:function(ag,ac,af){var ad=this.view.canvas_manager.dummy_context,ae=this.slotters[ag];if(!ae||(ae.mode!==af)){ae=new (u.FeatureSlotter)(ag,af,B,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.extra_info==="no_detail"||this.is_overview){mode="no_detail"}else{if(this.view.high-this.view.low>I){mode="Squish"}else{mode="Pack"}}return mode},get_canvas_height:function(ac,ag,ah,ad){if(ag==="Coverage"||ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var af=this.incremental_slots(ah,ac.data,ag);var ae=new (this.painter)(null,null,null,this.prefs,ag);return Math.max(this.min_height_px,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,af,aj,ae){var ap=this,ad=aq.canvas,ax=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(am.dataset_type==="bigwig"){return this._draw_line_track_tile(am,aq,ao,af,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var ar=0,au=am.data.length;ar<au;ar++){var ah=am.data[ar];var at=false;var al;for(var aw=0,aB=ak.length;aw<aB;aw++){al=ak[aw];al.update_attrs(ah);if(!al.keep(ah)){at=true;break}}if(!at){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aA=(this.filters_manager.alpha_filter?new E(this.filters_manager.alpha_filter):null),ay=(this.filters_manager.height_filter?new E(this.filters_manager.height_filter):null),az=new (this.painter)(ai,ax,ac,this.prefs,ao,aA,ay,ae,function(aC){return ap.view.get_base_color(aC)});var av=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){av=az.draw(aq,ad.width,ad.height,aj,an);av.translation=-ag}return new O(ap,af,aj,ad,am.data,ao,am.message,all_slotted,av)}});var Z=function(ad,ac,ae){N.call(this,ad,ac,ae);this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Histogram color",type:"color",default_value:l.get_random_color()},{key:"show_sample_data",label:"Show sample data",type:"bool",default_value:true},{key:"show_labels",label:"Show summary and sample labels",type:"bool",default_value:true},{key:"summary_height",label:"Locus summary height",type:"float",default_value:20},{key:"mode",type:"string",default_value:this.mode,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,af,ah,ag,ai){if(ac.dataset_type==="bigwig"){return this._draw_line_track_tile(ac,af,"Histogram",ag,ai)}else{var ae=this.view,ad=new (this.painter)(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah,function(aj){return ae.get_base_color(aj)});ad.draw(af,af.canvas.width,af.canvas.height,ai);return new c(this,ag,ai,af.canvas,ac.data)}},get_canvas_height:function(ac,ag,ah,ae){if(ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var ad=(this.dataset.get_metadata("sample_names")?this.dataset.get_metadata("sample_names").length:0);if(ad===0&&ac.data.length!==0){ad=ac.data[0][7].match(/,/g);if(ad===null){ad=1}else{ad=ad.length+1}}var af=new (this.painter)(null,null,null,this.prefs,ag);return af.get_required_height(ad)}},predraw_init:function(){var ac=[g.prototype.predraw_init.call(this)];if(!this.dataset.get_metadata("sample_names")){ac.push(this.dataset.fetch())}return ac},postdraw_actions:function(ag,ah,aj,ad){N.prototype.postdraw_actions.call(this,ag,ah,aj,ad);var af=ab.filter(ag,function(ak){return(ak instanceof M)});var ae=this.dataset.get_metadata("sample_names");if(af.length===0&&this.prefs.show_labels&&ae){var ac;if(this.container_div.find(".yaxislabel.variant").length===0){ac=this.prefs.summary_height/2;this.tiles_div.prepend($("<div/>").text("Summary").addClass("yaxislabel variant top").css({"font-size":ac+"px",top:(this.prefs.summary_height-ac)/2+"px"}));if(this.prefs.show_sample_data){var ai=ae.join("<br/>");this.tiles_div.prepend($("<div/>").html(ai).addClass("yaxislabel variant top sample").css({top:this.prefs.summary_height+2,}))}}ac=(this.mode==="Squish"?5:10)+"px";$(this.tiles_div).find(".sample").css({"font-size":ac,"line-height":ac});$(this.tiles_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel.variant").remove()}}});var T=function(ad,ac,ae){d.call(this,ad,ac,ae);this.painter=(ad.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(T.prototype,r.prototype,N.prototype,d.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block and sense strand color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_insertions",label:"Show insertions",type:"bool",default_value:false},{key:"show_differences",label:"Show differences only",type:"bool",default_value:true},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})}});var e={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:d,LineTrack:h,ReadTrack:T,VariantTrack:Z,VcfTrack:Z};var p=function(ae,ad,ac){if("copy" in ae){return ae.copy(ac)}else{var af=ae.obj_type;if(!af){af=ae.track_type}return new e[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:d,DiagonalHeatmapTrack:t,ReadTrack:T,VariantTrack:Z,CompositeTrack:f,object_from_template:p}});
\ No newline at end of file
+define(["libs/underscore","viz/visualization","viz/trackster/util","viz/trackster/slotting","viz/trackster/painters","viz/trackster/filters","mvc/data","mvc/tools"],function(ab,y,l,u,L,i,X,R){var q=ab.extend;var n={};var k=function(ac,ad){n[ac.attr("id")]=ad};var m=function(ac,ae,ag,af){ag=".group";var ad={};n[ac.attr("id")]=af;ac.bind("drag",{handle:"."+ae,relative:true},function(ao,ap){var an=$(this),at=$(this).parent(),ak=at.children(),am=n[$(this).attr("id")],aj,ai,aq,ah,al;ai=$(this).parents(ag);if(ai.length!==0){aq=ai.position().top;ah=aq+ai.outerHeight();var ar=n[ai.attr("id")];if(ap.offsetY<aq){$(this).insertBefore(ai);ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);ar.remove_drawable(am);ar.container.add_drawable(am);return}}}ai=null;for(al=0;al<ak.length;al++){aj=$(ak.get(al));aq=aj.position().top;ah=aq+aj.outerHeight();if(aj.is(ag)&&this!==aj.get(0)&&ap.offsetY>=aq&&ap.offsetY<=ah){if(ap.offsetY-aq<ah-ap.offsetY){aj.find(".content-div").prepend(this)}else{aj.find(".content-div").append(this)}if(am.container){am.container.remove_drawable(am)}n[aj.attr("id")].add_drawable(am);return}}for(al=0;al<ak.length;al++){aj=$(ak.get(al));if(ap.offsetY<aj.position().top&&!(aj.hasClass("reference-track")||aj.hasClass("intro"))){break}}if(al===ak.length){if(this!==ak.get(al-1)){at.append(this);n[at.attr("id")].move_drawable(am,al)}}else{if(this!==ak.get(al)){$(this).insertBefore(ak.get(al));n[at.attr("id")].move_drawable(am,(ap.deltaY>0?al-1:al))}}}).bind("dragstart",function(){ad["border-top"]=ac.css("border-top");ad["border-bottom"]=ac.css("border-bottom");$(this).css({"border-top":"1px solid blue","border-bottom":"1px solid blue"})}).bind("dragend",function(){$(this).css(ad)})};var F=20,B=100,I=12000,S=400,K=5000,x=100,o="Cannot display dataset due to an error. ",J="A converter for this dataset is not installed. Please check your datatypes_conf.xml file.",G="No data for this chrom/contig.",w="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",z="Tool cannot be rerun: ",b="Loading data...",U="Ready for display",Q=10,H=20,C=["Histogram","Line","Filled","Intensity"];function V(ad,ac){if(!ac){ac=0}var ae=Math.pow(10,ac);return Math.round(ad*ae)/ae}var r=function(ad,ac,af){if(!r.id_counter){r.id_counter=0}this.id=r.id_counter++;this.view=ad;this.container=ac;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.config=new j({params:this.config_params,onchange:this.config_onchange,saved_values:af.prefs});this.prefs=this.config.get("values");if(!this.prefs.name){this.prefs.name=af.name}if(this.config_onchange){this.config.on("change:values",this.config_onchange,this)}this.container_div=this.build_container_div();this.header_div=this.build_header_div();if(this.header_div){this.container_div.append(this.header_div);this.icons_div=$("<div/>").css("float","left").hide().appendTo(this.header_div);this.build_action_icons(this.action_icons_def);this.header_div.append($("<div style='clear: both'/>"));this.header_div.dblclick(function(ag){ag.stopPropagation()});var ae=this;this.container_div.hover(function(){ae.icons_div.show()},function(){ae.icons_div.hide()});$("<div style='clear: both'/>").appendTo(this.container_div)}};r.prototype.action_icons_def=[{name:"toggle_icon",title:"Hide/show content",css_class:"toggle",on_click_fn:function(ac){if(ac.prefs.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.prefs.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.prefs.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var ac=new a({model:ad.config});ac.render()}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".tooltip").remove();ac.remove()}}];q(r.prototype,{config_params:[{key:"name",label:"Name",type:"text",default_value:""},{key:"content_visible",type:"bool",default_value:true,hidden:true}],config_onchange:function(){this.track.set_name(this.track.config.get("values").name)},init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.prefs.content_visible){return true}return false},request_draw:function(){},_draw:function(ac){},to_dict:function(){},set_name:function(ac){this.old_name=this.prefs.name;this.prefs.name=ac;this.name_div.text(this.prefs.name)},revert_name:function(){if(this.old_name){this.prefs.name=this.old_name;this.name_div.text(this.prefs.name)}},remove:function(){this.changed();this.container.remove_drawable(this);var ac=this.view;this.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})},build_container_div:function(){},build_header_div:function(){},add_action_icon:function(ad,ai,ah,ag,ac,af){var ae=this;this.action_icons[ad]=$("<a/>").attr("title",ai).addClass("icon-button").addClass(ah).tooltip().click(function(){ag(ae)}).appendTo(this.icons_div);if(af){this.action_icons[ad].hide()}},build_action_icons:function(ac){var ae;for(var ad=0;ad<ac.length;ad++){ae=ac[ad];this.add_action_icon(ae.name,ae.title,ae.css_class,ae.on_click_fn,ae.prepend,ae.hide)}},update_icons:function(){},hide_contents:function(){},show_contents:function(){},get_drawables:function(){}});var A=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(A.prototype,r.prototype,{unpack_drawables:function(ae){this.drawables=[];var ad;for(var ac=0;ac<ae.length;ac++){ad=p(ae[ac],this.view,this);this.add_drawable(ad)}},init:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].init()}},_draw:function(ac){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad]._draw(ac)}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{prefs:this.prefs,obj_type:this.obj_type,drawables:ad}},add_drawable:function(ac){this.drawables.push(ac);ac.container=this;this.changed()},add_drawable_before:function(ae,ac){this.changed();var ad=this.drawables.indexOf(ac);if(ad!==-1){this.drawables.splice(ad,0,ae);return true}return false},replace_drawable:function(ae,ac,ad){var af=this.drawables.indexOf(ae);if(af!==-1){this.drawables[af]=ac;if(ad){ae.container_div.replaceWith(ac.container_div)}this.changed()}return af},remove_drawable:function(ad){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);ad.container=null;this.changed();return true}return false},move_drawable:function(ad,ae){var ac=this.drawables.indexOf(ad);if(ac!==-1){this.drawables.splice(ac,1);this.drawables.splice(ae,0,ad);this.changed();return true}return false},get_drawables:function(){return this.drawables},get_tracks:function(af){var ac=this.drawables.slice(0),ad=[],ae;while(ac.length!==0){ae=ac.shift();if(ae instanceof af){ad.push(ae)}else{if(ae.drawables){ac=ac.concat(ae.drawables)}}}return ad}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});A.call(this,ad,ac,af);this.content_div=$("<div/>").addClass("content-div").attr("id","group_"+this.id+"_content_div").appendTo(this.container_div);k(this.container_div,this);k(this.content_div,this);m(this.container_div,this.drag_handle_class,".group",this);this.filters_manager=new i.FiltersManager(this);this.header_div.after(this.filters_manager.parent_div);this.saved_filters_managers=[];if("drawables" in af){this.unpack_drawables(af.drawables)}if("filters" in af){var ae=this.filters_manager;this.filters_manager=new i.FiltersManager(this,af.filters);ae.parent_div.replaceWith(this.filters_manager.parent_div);if(af.filters.visible){this.setup_multitrack_filtering()}}};q(P.prototype,r.prototype,A.prototype,{action_icons_def:[r.prototype.action_icons_def[0],r.prototype.action_icons_def[1],{name:"composite_icon",title:"Show composite track",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_composite_track()}},{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters();ac._restore_filter_managers()}else{ac.setup_multitrack_filtering();ac.request_draw({clear_tile_cache:true})}ac.filters_manager.toggle()}},r.prototype.action_icons_def[2]],build_container_div:function(){var ac=$("<div/>").addClass("group").attr("id","group_"+this.id);if(this.container){this.container.content_div.append(ac)}return ac},build_header_div:function(){var ac=$("<div/>").addClass("track-header");ac.append($("<div/>").addClass(this.drag_handle_class));this.name_div=$("<div/>").addClass("track-name").text(this.prefs.name).appendTo(ac);return ac},hide_contents:function(){this.tiles_div.hide()},show_contents:function(){this.tiles_div.show();this.request_draw()},update_icons:function(){var ae=this.drawables.length;if(ae===0){this.action_icons.composite_icon.hide();this.action_icons.filters_icon.hide()}else{if(ae===1){if(this.drawables[0] instanceof f){this.action_icons.composite_icon.show()}this.action_icons.filters_icon.hide()}else{var al,ak,ai,ao=true,ag=this.drawables[0].get_type(),ac=0;for(al=0;al<ae;al++){ai=this.drawables[al];if(ai.get_type()!==ag){can_composite=false;break}if(ai instanceof d){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".tooltip").remove()}if(ac>1&&ac===this.drawables.length){var ap={},ad;ai=this.drawables[0];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];ap[ad.name]=[ad]}for(al=1;al<this.drawables.length;al++){ai=this.drawables[al];for(ak=0;ak<ai.filters_manager.filters.length;ak++){ad=ai.filters_manager.filters[ak];if(ad.name in ap){ap[ad.name].push(ad)}}}this.filters_manager.remove_all();var af,ah,aj,am;for(var an in ap){af=ap[an];if(af.length===ac){ah=new i.NumberFilter({name:af[0].name,index:af[0].index});this.filters_manager.add_filter(ah)}}if(this.filters_manager.filters.length>0){this.action_icons.filters_icon.show()}else{this.action_icons.filters_icon.hide()}}else{this.action_icons.filters_icon.hide()}}}},_restore_filter_managers:function(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac].filters_manager=this.saved_filters_managers[ac]}this.saved_filters_managers=[]},setup_multitrack_filtering:function(){if(this.filters_manager.filters.length>0){this.saved_filters_managers=[];for(var ac=0;ac<this.drawables.length;ac++){drawable=this.drawables[ac];this.saved_filters_managers.push(drawable.filters_manager);drawable.filters_manager=this.filters_manager}}this.filters_manager.init_filters()},show_composite_track:function(){var ad=new f(this.view,this.view,{name:this.prefs.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ad,true);ad.request_draw()},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){A.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(A.prototype.to_dict.call(this),{filters:this.filters_manager.to_dict()});if(this.filters_manager.visible()){this.setup_multitrack_filtering()}return ac},request_draw:function(ac){ab.each(this.drawables,function(ad){ad.request_draw(ac)})}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});A.call(this,"View",ac.container,ac);this.chrom=null;this.vis_id=ac.vis_id;this.dbkey=ac.dbkey;this.label_tracks=[];this.tracks_to_be_redrawn=[];this.max_low=0;this.max_high=0;this.zoom_factor=3;this.min_separation=30;this.has_changes=false;this.load_chroms_deferred=null;this.render();this.canvas_manager=new y.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new j({track:this,params:[{key:"a_color",label:"A Color",type:"color",default_value:"#FF0000"},{key:"c_color",label:"C Color",type:"color",default_value:"#00FF00"},{key:"g_color",label:"G Color",type:"color",default_value:"#0000FF"},{key:"t_color",label:"T Color",type:"color",default_value:"#FF00FF"},{key:"n_color",label:"N Color",type:"color",default_value:"#AAAAAA"}],saved_values:ac.prefs,onchange:function(){track.request_redraw({clear_tile_cache:true})}})},render:function(){this.requested_redraw=false;var ae=this.container,ac=this;this.top_container=$("<div/>").addClass("top-container").appendTo(ae);this.browser_content_div=$("<div/>").addClass("content").css("position","relative").appendTo(ae);this.bottom_container=$("<div/>").addClass("bottom-container").appendTo(ae);this.top_labeltrack=$("<div/>").addClass("top-labeltrack").appendTo(this.top_container);this.viewport_container=$("<div/>").addClass("viewport-container").attr("id","viewport-container").appendTo(this.browser_content_div);this.content_div=this.viewport_container;k(this.viewport_container,ac);this.intro_div=$("<div/>").addClass("intro").appendTo(this.viewport_container).hide();var af=$("<div/>").text("Add Datasets to Visualization").addClass("action-button").appendTo(this.intro_div).click(function(){y.select_datasets(galaxy_config.root+"visualization/list_current_history_datasets",galaxy_config.root+"api/datasets",{"f-dbkey":ac.dbkey},function(ag){ab.each(ag,function(ah){ac.add_drawable(p(ah,ac,ac))})})});this.nav_labeltrack=$("<div/>").addClass("nav-labeltrack").appendTo(this.bottom_container);this.nav_container=$("<div/>").addClass("trackster-nav-container").prependTo(this.top_container);this.nav=$("<div/>").addClass("trackster-nav").appendTo(this.nav_container);this.overview=$("<div/>").addClass("overview").appendTo(this.bottom_container);this.overview_viewport=$("<div/>").addClass("overview-viewport").appendTo(this.overview);this.overview_close=$("<a/>").attr("title","Close overview").addClass("icon-button overview-close tooltip").hide().appendTo(this.overview_viewport);this.overview_highlight=$("<div/>").addClass("overview-highlight").hide().appendTo(this.overview_viewport);this.overview_box_background=$("<div/>").addClass("overview-boxback").appendTo(this.overview_viewport);this.overview_box=$("<div/>").addClass("overview-box").appendTo(this.overview_viewport);this.default_overview_height=this.overview_box.height();this.nav_controls=$("<div/>").addClass("nav-controls").appendTo(this.nav);this.chrom_select=$("<select/>").attr({name:"chrom"}).css("width","15em").append("<option value=''>Loading</option>").appendTo(this.nav_controls);var ad=function(ag){if(ag.type==="focusout"||(ag.keyCode||ag.which)===13||(ag.keyCode||ag.which)===27){if((ag.keyCode||ag.which)!==27){ac.go_to($(this).val())}$(this).hide();$(this).val("");ac.location_span.show();ac.chrom_select.show()}};this.nav_input=$("<input/>").addClass("nav-input").hide().bind("keyup focusout",ad).appendTo(this.nav_controls);this.location_span=$("<span/>").addClass("location").attr("original-title","Click to change location").tooltip({placement:"bottom"}).appendTo(this.nav_controls);this.location_span.click(function(){ac.location_span.hide();ac.chrom_select.hide();ac.nav_input.val(ac.chrom+":"+ac.low+"-"+ac.high);ac.nav_input.css("display","inline-block");ac.nav_input.select();ac.nav_input.focus();ac.nav_input.autocomplete({source:function(ai,ag){var aj=[],ah=$.map(ac.get_tracks(d),function(ak){return ak.data_manager.search_features(ai.term).success(function(al){aj=aj.concat(al)})});$.when.apply($,ah).done(function(){ag($.map(aj,function(ak){return{label:ak[0],value:ak[1]}}))})}})});if(this.vis_id!==undefined){this.hidden_input=$("<input/>").attr("type","hidden").val(this.vis_id).appendTo(this.nav_controls)}this.zo_link=$("<a/>").attr("id","zoom-out").attr("title","Zoom out").tooltip({placement:"bottom"}).click(function(){ac.zoom_out();ac.request_redraw()}).appendTo(this.nav_controls);this.zi_link=$("<a/>").attr("id","zoom-in").attr("title","Zoom in").tooltip({placement:"bottom"}).click(function(){ac.zoom_in();ac.request_redraw()}).appendTo(this.nav_controls);this.load_chroms_deferred=this.load_chroms({low:0});this.chrom_select.bind("change",function(){ac.change_chrom(ac.chrom_select.val())});this.browser_content_div.click(function(ag){$(this).find("input").trigger("blur")});this.browser_content_div.bind("dblclick",function(ag){ac.zoom_in(ag.pageX,this.viewport_container)});this.overview_box.bind("dragstart",function(ag,ah){this.current_x=ah.offsetX}).bind("drag",function(ag,ai){var aj=ai.offsetX-this.current_x;this.current_x=ai.offsetX;var ah=Math.round(aj/ac.viewport_container.width()*(ac.max_high-ac.max_low));ac.move_delta(-ah)});this.overview_close.click(function(){ac.reset_overview()});this.viewport_container.bind("draginit",function(ag,ah){if(ag.clientX>ac.viewport_container.width()-16){return false}}).bind("dragstart",function(ag,ah){ah.original_low=ac.low;ah.current_height=ag.clientY;ah.current_x=ah.offsetX}).bind("drag",function(ai,ak){var ag=$(this);var al=ak.offsetX-ak.current_x;var ah=ag.scrollTop()-(ai.clientY-ak.current_height);ag.scrollTop(ah);ak.current_height=ai.clientY;ak.current_x=ak.offsetX;var aj=Math.round(al/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}).bind("mousewheel",function(ai,ak,ah,ag){if(ah){ah*=50;var aj=Math.round(-ah/ac.viewport_container.width()*(ac.high-ac.low));ac.move_delta(aj)}});this.top_labeltrack.bind("dragstart",function(ag,ah){return $("<div />").css({height:ac.browser_content_div.height()+ac.top_labeltrack.height()+ac.nav_labeltrack.height()+1,top:"0px",position:"absolute","background-color":"#ccf",opacity:0.5,"z-index":1000}).appendTo($(this))}).bind("drag",function(ak,al){$(al.proxy).css({left:Math.min(ak.pageX,al.startX)-ac.container.offset().left,width:Math.abs(ak.pageX-al.startX)});var ah=Math.min(ak.pageX,al.startX)-ac.container.offset().left,ag=Math.max(ak.pageX,al.startX)-ac.container.offset().left,aj=(ac.high-ac.low),ai=ac.viewport_container.width();ac.update_location(Math.round(ah/ai*aj)+ac.low,Math.round(ag/ai*aj)+ac.low)}).bind("dragend",function(al,am){var ah=Math.min(al.pageX,am.startX),ag=Math.max(al.pageX,am.startX),aj=(ac.high-ac.low),ai=ac.viewport_container.width(),ak=ac.low;ac.low=Math.round(ah/ai*aj)+ak;ac.high=Math.round(ag/ai*aj)+ak;$(am.proxy).remove();ac.request_redraw()});this.add_label_track(new W(this,{content_div:this.top_labeltrack}));this.add_label_track(new W(this,{content_div:this.nav_labeltrack}));$(window).bind("resize",function(){if(this.resize_timer){clearTimeout(this.resize_timer)}this.resize_timer=setTimeout(function(){ac.resize_window()},500)});$(document).bind("redraw",function(){ac.redraw()});this.reset();$(window).trigger("resize")},get_base_color:function(ac){return this.config.get("values")[ac.toLowerCase()+"_color"]||this.config.get("values").n_color}});q(Y.prototype,A.prototype,{changed:function(){this.has_changes=true},update_intro_div:function(){if(this.drawables.length===0){this.intro_div.show()}else{this.intro_div.hide()}},trigger_navigate:function(ad,af,ac,ag){if(this.timer){clearTimeout(this.timer)}if(ag){var ae=this;this.timer=setTimeout(function(){ae.trigger("navigate",ad+":"+af+"-"+ac)},500)}else{view.trigger("navigate",ad+":"+af+"-"+ac)}},update_location:function(ac,ae){this.location_span.text(commatize(ac)+" - "+commatize(ae));this.nav_input.val(this.chrom+":"+commatize(ac)+"-"+commatize(ae));var ad=view.chrom_select.val();if(ad!==""){this.trigger_navigate(ad,view.low,view.high,true)}},load_chroms:function(ae){ae.num=x;var ac=this,ad=$.Deferred();$.ajax({url:galaxy_config.root+"api/genomes/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){var ah=new D(ac);ac.add_label_track(ah);ac.reference_track=ah}ac.chrom_data=ag.chrom_info;var ak='<option value="">Select Chrom/Contig</option>';for(var aj=0,af=ac.chrom_data.length;aj<af;aj++){var ai=ac.chrom_data[aj].chrom;ak+='<option value="'+ai+'">'+ai+"</option>"}if(ag.prev_chroms){ak+='<option value="previous">Previous '+x+"</option>"}if(ag.next_chroms){ak+='<option value="next">Next '+x+"</option>"}ac.chrom_select.html(ak);ac.chrom_start_index=ag.start_index;ad.resolve(ag.chrom_info)},error:function(){alert("Could not load chroms for this dbkey:",ac.dbkey)}});return ad},change_chrom:function(ah,ad,aj){var ae=this;if(!ae.chrom_data){ae.load_chroms_deferred.then(function(){ae.change_chrom(ah,ad,aj)});return}if(!ah||ah==="None"){return}if(ah==="previous"){ae.load_chroms({low:this.chrom_start_index-x});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+x});return}var ai=$.grep(ae.chrom_data,function(ak,al){return ak.chrom===ah})[0];if(ai===undefined){ae.load_chroms({chrom:ah},function(){ae.change_chrom(ah,ad,aj)});return}else{if(ah!==ae.chrom){ae.chrom=ah;ae.chrom_select.val(ae.chrom);ae.max_high=ai.len-1;ae.reset();for(var ag=0,ac=ae.drawables.length;ag<ac;ag++){var af=ae.drawables[ag];if(af.init){af.init()}}if(ae.reference_track){ae.reference_track.init()}}if(ad&&aj){ae.low=Math.max(ad,0);ae.high=Math.min(aj,ae.max_high)}else{ae.low=0;ae.high=ae.max_high}ae.reset_overview();ae.request_redraw()}},go_to:function(ag){ag=ag.replace(/,/g,"");ag=ag.replace(/:|\-/g," ");var ad=ag.split(/\s+/),af=ad[0],ae=(ad[1]?parseInt(ad[1],10):null),ac=(ad[2]?parseInt(ad[2],10):null);if(!ac){ae=ae-15;ac=ae+15}this.change_chrom(af,ae,ac)},move_fraction:function(ae){var ac=this;var ad=ac.high-ac.low;this.move_delta(ae*ad)},move_delta:function(af){var ac=this;var ae=ac.high-ac.low;if(ac.low-af<ac.max_low){ac.low=ac.max_low;ac.high=ac.max_low+ae}else{if(ac.high-af>ac.max_high){ac.high=ac.max_high;ac.low=ac.max_high-ae}else{ac.high-=af;ac.low-=af}}ac.request_redraw({data_fetch:false});if(this.redraw_on_move_fn){clearTimeout(this.redraw_on_move_fn)}this.redraw_on_move_fn=setTimeout(function(){ac.request_redraw()},200);var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){A.prototype.add_drawable.call(this,ac);ac.init();this.changed();this.update_intro_div()},add_label_track:function(ac){ac.view=this;ac.init();this.label_tracks.push(ac)},remove_drawable:function(ae,ad){A.prototype.remove_drawable.call(this,ae);if(ad){var ac=this;ae.container_div.hide(0,function(){$(this).remove();ac.update_intro_div()})}},reset:function(){this.low=this.max_low;this.high=this.max_high;this.viewport_container.find(".yaxislabel").remove()},request_redraw:function(ad,ae){var ac=this,af=(ae?[ae]:ac.drawables);ab.each(af,function(ag){var ah=ab.find(ac.tracks_to_be_redrawn,function(ai){return ai[0]===ag});if(ah){ah[1]=ad}else{ac.tracks_to_be_redrawn.push([ag,ad])}});if(!this.requested_redraw){requestAnimationFrame(function(){ac._redraw()});this.requested_redraw=true}},_redraw:function(){this.requested_redraw=false;var ac=this.low,ag=this.high;if(ac<this.max_low){ac=this.max_low}if(ag>this.max_high){ag=this.max_high}var ad=this.high-this.low;if(this.high!==0&&ad<this.min_separation){ag=ac+this.min_separation}this.low=Math.floor(ac);this.high=Math.ceil(ag);this.update_location(this.low,this.high);this.resolution_px_b=this.viewport_container.width()/(this.high-this.low);var af=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ah=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ae=13;this.overview_box.css({left:af,width:Math.max(ae,ah)}).show();if(ah<ae){this.overview_box.css("left",af-(ae-ah)/2)}if(this.overview_highlight){this.overview_highlight.css({left:af,width:ah})}ab.each(this.tracks_to_be_redrawn,function(ak){var ai=ak[0],aj=ak[1];if(ai){ai._draw(aj)}});this.tracks_to_be_redrawn=[];ab.each(this.label_tracks,function(ai){ai._draw()})},zoom_in:function(ad,ae){if(this.max_high===0||this.high-this.low<=this.min_separation){return}var af=this.high-this.low,ag=af/2+this.low,ac=(af/this.zoom_factor)/2;if(ad){ag=ad/this.viewport_container.width()*(this.high-this.low)+this.low}this.low=Math.round(ag-ac);this.high=Math.round(ag+ac);this.changed();this.request_redraw()},zoom_out:function(){if(this.max_high===0){return}var ad=this.high-this.low,ae=ad/2+this.low,ac=(ad*this.zoom_factor)/2;this.low=Math.round(ae-ac);this.high=Math.round(ae+ac);this.changed();this.request_redraw()},resize_window:function(){this.viewport_container.height(this.container.height()-this.top_container.height()-this.bottom_container.height());this.request_redraw()},set_overview:function(ae){if(this.overview_drawable){if(this.overview_drawable.dataset.id===ae.dataset.id){return}this.overview_viewport.find(".track").remove()}var ad=ae.copy({content_div:this.overview_viewport}),ac=this;ad.header_div.hide();ad.is_overview=true;ac.overview_drawable=ad;this.overview_drawable.postdraw_actions=function(){ac.overview_highlight.show().height(ac.overview_drawable.content_div.height());ac.overview_viewport.height(ac.overview_drawable.content_div.height()+ac.overview_box.outerHeight());ac.overview_close.show();ac.resize_window()};ac.overview_drawable.request_draw();this.changed()},reset_overview:function(){$(".tooltip").remove();this.overview_viewport.find(".track-tile").remove();this.overview_viewport.height(this.default_overview_height);this.overview_box.height(this.default_overview_height);this.overview_close.hide();this.overview_highlight.hide();view.resize_window();view.overview_drawable=null}});var s=R.Tool.extend({defaults:{track:null},initialize:function(ac){if(ac.tool_state!==undefined){this.set("hidden",ac.tool_state.hidden)}this.remove_inputs(["data","hidden_data","conditional"])},state_dict:function(ac){return ab.extend(this.get_inputs_dict(),{hidden:!this.is_visible()})}});var v=Backbone.View.extend({events:{"change input":"update_value"},render:function(){var ae=this.$el.addClass("param-row"),af=this.model;var ac=$("<div>").addClass("param-label").text(af.get("label")).appendTo(ae);var ad=$("<div/>").addClass("param-input").html(af.get("html")).appendTo(ae);ad.find(":input").val(af.get("value"));$("<div style='clear: both;'/>").appendTo(ae)},update_value:function(ac){this.model.set_value($(ac.target).val())}});var aa=Backbone.View.extend({initialize:function(ac){this.model.on("change:hidden",this.set_visible,this)},render:function(){var ad=this;tool=this.model,parent_div=this.$el.addClass("dynamic-tool").hide();parent_div.bind("drag",function(ah){ah.stopPropagation()}).click(function(ah){ah.stopPropagation()}).bind("dblclick",function(ah){ah.stopPropagation()}).keydown(function(ah){ah.stopPropagation()});var ae=$("<div class='tool-name'>").appendTo(parent_div).text(tool.get("name"));tool.get("inputs").each(function(ai){var ah=new v({model:ai});ah.render();parent_div.append(ah.$el)});parent_div.find("input").click(function(){$(this).select()});var af=$("<div>").addClass("param-row").appendTo(parent_div);var ag=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(af);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(af);ac.click(function(){ad.run_on_region()});ag.click(function(){ad.run_on_dataset()});if(tool.is_visible()){this.$el.show()}},set_visible:function(){if(this.model.is_visible()){this.$el.show()}else{this.$el.hide()}},update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},run_on_dataset:function(){var ac=this.model;this.run({target_dataset_id:this.model.get("track").dataset.id,action:"rerun",tool_id:ac.id},null,function(ad){Galaxy.modal.show({title:ac.get("name")+" is Running",body:ac.get("name")+" is running on the complete dataset. Tool outputs are in dataset's history.",buttons:{Close:function(){Galaxy.modal.hide()}}})})},run_on_region:function(){var ad=this.model.get("track"),ag=this.model,ai=new y.GenomeRegion({chrom:ad.view.chrom,start:ad.view.low,end:ad.view.high}),aj={target_dataset_id:ad.dataset.id,action:"rerun",tool_id:ag.id,regions:[ai.toJSON()]},ah=ad,al=aj.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ak=new P(view,view,{name:this.prefs.name});var af=ah.container.replace_drawable(ah,ak,false);ak.container_div.insertBefore(ah.view.content_div.children()[af]);ak.add_drawable(ah);ah.container_div.appendTo(ak.content_div);ac=ak}else{ac=ah.container}var ae=new ah.constructor(view,ac,{name:al,hda_ldda:"hda"});ae.init_for_tool_data();ae.change_mode(ah.mode);ae.set_filters_manager(ah.filters_manager.copy(ae));ae.update_icons();ac.add_drawable(ae);ae.tiles_div.text("Starting job.");this.run(aj,ae,function(am){ae.set_dataset(new X.Dataset(am));ae.tiles_div.text("Running job.");ae.init()})},run:function(ac,ae,af){ac.inputs=this.model.get_inputs_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_config.root+"api/tools",data:JSON.stringify(ac),dataType:"json",contentType:"application/json",type:"POST"},interval:2000,success_fn:function(ag){return ag!=="pending"}});$.when(ad.go()).then(function(ag){if(ag==="no converter"){ae.container_div.addClass("error");ae.content_div.text(J)}else{if(ag.error){ae.container_div.addClass("error");ae.content_div.text(z+ag.message)}else{af(ag)}}})}});var E=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};E.prototype.gen_val=function(ac){if(this.filter.high===Number.MAX_VALUE||this.filter.low===-Number.MAX_VALUE||this.filter.low===this.filter.high){return this.default_val}return((parseFloat(ac[this.filter.index])-this.filter.low)/(this.filter.high-this.filter.low))};var j=Backbone.Model.extend({initialize:function(ad){var ac={};ab.each(ad.params,function(ae){ac[ae.key]=ae.default_value});if(ad.saved_values){ab.each(this.get("params"),function(ae){if(ae.key in ad.saved_values){ac[ae.key]=ad.saved_values[ae.key]}})}this.set("values",ac)},set_param_default_value:function(ad,ac){var ae=ab.find(this.get("params"),function(af){return af.key===ad});if(ae){ae.default_value=ac}},set_param_value:function(ac,ad){var ae=ab.find(this.get("params"),function(af){return af.key===ac});if(ae){if(typeof ad==="string"||ad instanceof String){if(ad.trim()===""){ad=ae.default_value}else{if(ae.type==="float"){ad=parseFloat(ad)}else{if(ae.type==="int"){ad=parseInt(ad,10)}}}}}if(this.get("values")[ac]!==ad){this.get("values")[ac]=ad;this.trigger("change:values");return true}else{return false}}});var a=Backbone.View.extend({render:function(){var aj=this.model;var ac=$("<div/>").keydown(function(ak){ak.stopPropagation()});var ai;function ah(ao,ak){for(var at=0;at<ao.length;at++){ai=ao[at];if(ai.hidden){continue}var am="param_"+at;var ax=aj.get("values")[ai.key];var az=$("<div class='form-row' />").appendTo(ak);az.append($("<label />").attr("for",am).text(ai.label+":"));if(ai.type==="bool"){az.append($('<input type="checkbox" />').attr("id",am).attr("name",am).attr("checked",ax))}else{if(ai.type==="text"){az.append($('<input type="text"/>').attr("id",am).val(ax).click(function(){$(this).select()}))}else{if(ai.type==="select"){var av=$("<select />").attr("id",am);for(var aq=0;aq<ai.options.length;aq++){$("<option/>").text(ai.options[aq].label).attr("value",ai.options[aq].value).appendTo(av)}av.val(ax);az.append(av)}else{if(ai.type==="color"){var ay=$("<div/>").appendTo(az),au=$("<input />").attr("id",am).attr("name",am).val(ax).css("float","left").appendTo(ay).click(function(aB){$(".tooltip").removeClass("in");var aA=$(this).siblings(".tooltip").addClass("in");aA.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top+Galaxy.modal.scrollTop()-($(aA).height()/2)+($(this).height()/2)}).show();aA.click(function(aC){aC.stopPropagation()});$(document).bind("click.color-picker",function(){aA.hide();$(document).unbind("click.color-picker")});aB.stopPropagation()}),ar=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(ay).attr("title","Set new random color").tooltip(),aw=$("<div class='tooltip right' style='position: absolute;' />").appendTo(ay).hide(),an=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(aw),al=$("<div class='tooltip-arrow'></div>").appendTo(aw),ap=$.farbtastic(an,{width:100,height:100,callback:au,color:ax});ay.append($("<div/>").css("clear","both"));(function(aA){ar.click(function(){aA.setColor(l.get_random_color())})})(ap)}else{az.append($("<input />").attr("id",am).attr("name",am).val(ax))}}}}if(ai.help){az.append($("<div class='help'/>").text(ai.help))}}}ah(aj.get("params"),ac);var ad=this,ag=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ae=function(){ad.update_from_form($(Galaxy.modal.el));Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},af=function(ak){if((ak.keyCode||ak.which)===27){ag()}else{if((ak.keyCode||ak.which)===13){ae()}}};$(window).bind("keypress.check_enter_esc",af);Galaxy.modal.show({title:"Configure",body:ac,buttons:{Cancel:ag,Ok:ae}})},update_from_form:function(ac){var ad=this.model;var ae=false;ab.each(ad.get("params"),function(ah,af){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}ae=ad.set_param_value(ah.key,ag)||ae}})}});var c=function(ac,af,ag,ad,ae){this.track=ac;this.region=af;this.low=af.get("start");this.high=af.get("end");this.w_scale=ag;this.canvas=ad;this.html_elt=$("<div class='track-tile'/>").append(ad);this.data=ae;this.stale=false};c.prototype.predisplay_actions=function(){};var M=function(ac,af,ag,ad,ae){c.call(this,ac,af,ag,ad,ae)};M.prototype.predisplay_actions=function(){};var O=function(af,am,ao,ae,ah,ai,ap,ad,al){c.call(this,af,am,ao,ae,ah);this.mode=ai;this.all_slotted=ad;this.feature_mapper=al;this.has_icons=false;if(ap){this.has_icons=true;var aj=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:F,width:ae.width}).prependTo(this.html_elt);var ak=new y.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),an=ah.length,ag=$("<a/>").addClass("icon more-down").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a/>").addClass("icon more-across").attr("title","For speed, only the first "+an+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ag.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.DEEP_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()});ac.click(function(){aj.stale=true;af.data_manager.get_more_data(ak,af.mode,1/aj.w_scale,{},af.data_manager.BROAD_DATA_REQ);$(".tooltip").hide();af.request_draw()}).dblclick(function(aq){aq.stopPropagation()})}};q(O.prototype,c.prototype);O.prototype.predisplay_actions=function(){var ad=this,ac={};if(ad.mode!=="Pack"){return}$(this.html_elt).hover(function(){this.hovered=true;$(this).mousemove()},function(){this.hovered=false;$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()}).mousemove(function(ao){if(!this.hovered){return}var aj=$(this).offset(),an=ao.pageX-aj.left,am=ao.pageY-aj.top,at=ad.feature_mapper.get_feature_data(an,am),ak=(at?at[0]:null);$(this).parents(".track-content").children(".overlay").children(".feature-popup").each(function(){if(!ak||$(this).attr("id")!==ak.toString()){$(this).remove()}});if(at){var af=ac[ak];if(!af){var ap={name:at[3],start:at[1],end:at[2],strand:at[4]},ai=ad.track.filters_manager.filters,ah;for(var al=0;al<ai.length;al++){ah=ai[al];ap[ah.name]=at[ah.index]}af=$("<div/>").attr("id",ak).addClass("feature-popup");var au=$("<table/>"),ar,aq,av;for(ar in ap){aq=ap[ar];av=$("<tr/>").appendTo(au);$("<th/>").appendTo(av).text(ar);$("<td/>").attr("align","left").appendTo(av).text(typeof(aq)==="number"?V(aq,2):aq)}af.append($("<div class='feature-popup-inner'>").append(au));ac[ak]=af}af.appendTo($(this).parents(".track-content").children(".overlay"));var ag=an+parseInt(ad.html_elt.css("left"),10)-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"),10)+7;af.css("left",ag+"px").css("top",ae+"px")}else{if(!ao.isPropagationStopped()){ao.stopPropagation();$(this).siblings().each(function(){$(this).trigger(ao)})}}}).mouseleave(function(){$(this).parents(".track-content").children(".overlay").children(".feature-popup").remove()})};var g=function(ad,ac,ae){q(ae,{drag_handle_class:"draghandle"});r.call(this,ad,ac,ae);this.dataset=null;if(ae.dataset){this.dataset=(ae.dataset instanceof Backbone.Model?ae.dataset:X.Dataset.findOrCreate(ae.dataset))}this.dataset_check_type="converted_datasets_state";this.data_url_extra_params={};this.data_query_wait=("data_query_wait" in ae?ae.data_query_wait:K);this.data_manager=("data_manager" in ae?ae.data_manager:new y.GenomeDataManager({dataset:this.dataset,genome:new y.Genome({key:ad.dbkey,chroms_info:{chrom_info:ad.chrom_data}}),data_mode_compatible:this.data_and_mode_compatible,can_subset:this.can_subset}));this.min_height_px=16;this.max_height_px=800;this.visible_height_px=this.prefs.height;this.content_div=$("<div class='track-content'>").appendTo(this.container_div);if(this.container){this.container.content_div.append(this.container_div);if(!("resize" in ae)||ae.resize){this.add_resize_handle()}}};q(g.prototype,r.prototype,{action_icons_def:[{name:"mode_icon",title:"Set display mode",css_class:"chevron-expand",on_click_fn:function(){}},r.prototype.action_icons_def[0],{name:"overview_icon",title:"Set as overview",css_class:"overview-icon",on_click_fn:function(ac){ac.view.set_overview(ac)}},r.prototype.action_icons_def[1],{name:"filters_icon",title:"Filters",css_class:"filters-icon",on_click_fn:function(ac){if(ac.filters_manager.visible()){ac.filters_manager.clear_filters()}else{ac.filters_manager.init_filters()}ac.filters_manager.toggle()}},{name:"tools_icon",title:"Tool",css_class:"hammer",on_click_fn:function(ac){ac.tool.toggle();if(ac.tool.is_visible()){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".tooltip").remove()}},{name:"param_space_viz_icon",title:"Tool parameter space visualization",css_class:"arrow-split",on_click_fn:function(ac){var af='<strong>Tool</strong>: <%= track.tool.name %><br/><strong>Dataset</strong>: <%= track.name %><br/><strong>Region(s)</strong>: <select name="regions"><option value="cur">current viewing area</option><option value="bookmarks">bookmarks</option><option value="both">current viewing area and bookmarks</option></select>',ae=ab.template(af,{track:ac});var ah=function(){Galaxy.modal.hide();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new y.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new y.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}Galaxy.modal.hide();window.location.href=galaxy_config.root+"visualization/sweepster?"+$.param({dataset_id:ac.dataset.id,hda_ldda:ac.dataset.get("hda_ldda"),regions:JSON.stringify(new Backbone.Collection(al).toJSON())})},ag=function(ai){if((ai.keyCode||ai.which)===27){ah()}else{if((ai.keyCode||ai.which)===13){ad()}}};Galaxy.modal.show({title:"Visualize tool parameter space and output from different parameter settings?",body:ae,buttons:{No:ah,Yes:ad}})}},r.prototype.action_icons_def[2]],can_draw:function(){return this.dataset&&r.prototype.can_draw.call(this)},build_container_div:function(){return $("<div/>").addClass("track").attr("id","track_"+this.id).css("position","relative")},build_header_div:function(){var ac=$("<div class='track-header'/>");if(this.view.editor){this.drag_div=$("<div/>").addClass(this.drag_handle_class).appendTo(ac)}this.name_div=$("<div/>").addClass("track-name").appendTo(ac).text(this.prefs.name).attr("id",this.prefs.name.replace(/\s+/g,"-").replace(/[^a-zA-Z0-9\-]/g,"").toLowerCase());return ac},set_dataset:function(ac){this.dataset=ac;this.data_manager.set("dataset",ac)},on_resize:function(){this.request_draw({clear_tile_cache:true})},add_resize_handle:function(){var ac=this;var af=false;var ae=false;var ad=$("<div class='track-resize'>");$(ac.container_div).hover(function(){if(ac.prefs.content_visible){af=true;ad.show()}},function(){af=false;if(!ae){ad.hide()}});ad.hide().bind("dragstart",function(ag,ah){ae=true;ah.original_height=$(ac.content_div).height()}).bind("drag",function(ah,ai){var ag=Math.min(Math.max(ai.original_height+ai.deltaY,ac.min_height_px),ac.max_height_px);$(ac.tiles_div).css("height",ag);ac.visible_height_px=(ac.max_height_px===ag?0:ag);ac.on_resize()}).bind("dragend",function(ag,ah){ac.tile_cache.clear();ae=false;if(!af){ad.hide()}ac.config.get("values").height=ac.visible_height_px;ac.changed()}).appendTo(ac.container_div)},set_display_modes:function(af,ai){this.display_modes=af;this.mode=(ai?ai:(this.config&&this.config.get("values").mode?this.config.get("values").mode:this.display_modes[0]));this.action_icons.mode_icon.attr("title","Set display mode (now: "+this.mode+")");var ad=this,ag={};for(var ae=0,ac=ad.display_modes.length;ae<ac;ae++){var ah=ad.display_modes[ae];ag[ah]=function(aj){return function(){ad.change_mode(aj);ad.icons_div.show();ad.container_div.mouseleave(function(){ad.icons_div.hide()})}}(ah)}make_popupmenu(this.action_icons.mode_icon,ag)},build_action_icons:function(){r.prototype.build_action_icons.call(this,this.action_icons_def);if(this.display_modes!==undefined){this.set_display_modes(this.display_modes)}},hide_contents:function(){this.tiles_div.hide();this.container_div.find(".yaxislabel, .track-resize").hide()},show_contents:function(){this.tiles_div.show();this.container_div.find(".yaxislabel, .track-resize").show();this.request_draw()},get_type:function(){if(this instanceof W){return"LabelTrack"}else{if(this instanceof D){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof T){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof d){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.tiles_div.css("height","auto");ad.tiles_div.text("").children().remove();ad.container_div.removeClass("nodata error pending");if(!ad.dataset.id){return}var ac=$.Deferred(),af={hda_ldda:ad.dataset.get("hda_ldda"),data_type:this.dataset_check_type,chrom:ad.view.chrom,retry:ae};$.getJSON(this.dataset.url(),af,function(ag){if(!ag||ag==="error"||ag.kind==="error"){ad.container_div.addClass("error");ad.tiles_div.text(o);if(ag.message){ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("View error").click(function(){Galaxy.modal.show({title:"Trackster Error",body:"<pre>"+ag.message+"</pre>",buttons:{Close:function(){Galaxy.modal.hide()}}})}));ad.tiles_div.append($("<span/>").text(" "));ad.tiles_div.append($("<a href='javascript:void(0);'></a>").text("Try again").click(function(){ad.init(true)}))}}else{if(ag==="no converter"){ad.container_div.addClass("error");ad.tiles_div.text(J)}else{if(ag==="no data"||(ag.data!==undefined&&(ag.data===null||ag.data.length===0))){ad.container_div.addClass("nodata");ad.tiles_div.text(G)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(w);setTimeout(function(){ad.init()},ad.data_query_wait)}else{if(ag==="data"||ag.status==="data"){if(ag.valid_chroms){ad.valid_chroms=ag.valid_chroms;ad.update_icons()}ad.tiles_div.text(U);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when.apply($,ad.predraw_init()).done(function(){ac.resolve();ad.container_div.removeClass("nodata error pending");ad.request_draw()})}else{ac.resolve()}}}}}}});this.update_icons();return ac},predraw_init:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){ac.container_div.addClass("line-track");var af=ad.data;if(af&&af.min&&af.max){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.config.set_param_default_value("min_value",ae);ac.config.set_param_default_value("max_value",ag);ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},get_drawables:function(){return this}});var N=function(ae,ad,ag){g.call(this,ae,ad,ag);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in ag?ag.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=(ag.tool?new s(ab.extend(ag.tool,{track:this,tool_state:ag.tool_state})):null);this.tile_cache=new y.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){var af=new aa({model:this.tool});af.render();this.dynamic_tool_div=af.$el;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);if(!this.prefs.content_visible){this.tiles_div.hide()}this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(ag.mode){this.change_mode(ag.mode)}};q(N.prototype,r.prototype,g.prototype,{action_icons_def:g.prototype.action_icons_def.concat([{name:"show_more_rows_icon",title:"To minimize track height, not all feature rows are displayed. Click to display more rows.",css_class:"exclamation",on_click_fn:function(ac){$(".tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw({clear_tile_cache:true})},hide:true}]),copy:function(ac){var ad=this.to_dict();q(ad,{data_manager:this.data_manager});var ae=new this.constructor(this.view,ac,ad);ae.change_mode(this.mode);ae.enabled=this.enabled;return ae},set_filters_manager:function(ac){this.filters_manager=ac;this.header_div.after(this.filters_manager.parent_div)},to_dict:function(){return{track_type:this.get_type(),dataset:{id:this.dataset.id,hda_ldda:this.dataset.get("hda_ldda")},prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},set_min_max:function(){var ac=this;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.dataset.get("hda_ldda")},function(ad){var af=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=af.min,ag=af.max;ae=Math.floor(Math.min(0,Math.max(ae,af.mean-2*af.sd)));ag=Math.ceil(Math.max(0,Math.min(ag,af.mean+2*af.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ag}})},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.get("values").mode=ad;if(ad==="Auto"){this.data_manager.clear()}ac.request_draw({clear_tile_cache:true});this.action_icons.mode_icon.attr("title","Set display mode (now: "+ac.mode+")");return ac},update_icons:function(){var ac=this;if(ac.filters_available){ac.action_icons.filters_icon.show()}else{ac.action_icons.filters_icon.hide()}if(ac.tool){ac.action_icons.tools_icon.show();ac.action_icons.param_space_viz_icon.show()}else{ac.action_icons.tools_icon.hide();ac.action_icons.param_space_viz_icon.hide()}},_gen_tile_cache_key:function(ad,ac){return ad+"_"+ac},request_draw:function(ac){if(ac&&ac.clear_tile_cache){this.tile_cache.clear()}this.view.request_redraw(ac,this)},before_draw:function(){this.max_height_px=0},_draw:function(aq){if(!this.can_draw()){return}var an=aq&&aq.clear_after,al=this.view.low,ag=this.view.high,aj=ag-al,ad=this.view.container.width(),ap=this.view.resolution_px_b,af=1/ap;if(this.is_overview){al=this.view.max_low;ag=this.view.max_high;ap=ad/(view.max_high-view.max_low);af=1/ap}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(af*S)),ak,am,ah,ai=[],ao=[];while((ac*S*af)<ag){ak=Math.floor(ac*S*af);am=new y.GenomeRegion({chrom:this.view.chrom,start:ak,end:Math.min(ak+Math.ceil(S*af),this.view.max_high)});ah=this.draw_helper(am,ap,aq);ai.push(ah);$.when(ah).then(function(ar){ao.push(ar)});ac+=1}if(!an){this.tiles_div.children(".remove").removeClass("remove").remove()}var ae=this;$.when.apply($,ai).then(function(){ae.tiles_div.children(".remove").remove();ao=ab.filter(ao,function(ar){return ar!==null});if(ao.length!==0){ae.postdraw_actions(ao,ad,ap,an)}})},_add_yaxis_label:function(af,ah){var ad=this,ag=(af==="max"?"top":"bottom"),ai=(af==="max"?"max":"min"),ac=(af==="max"?"max_value":"min_value"),ae=this.container_div.find(".yaxislabel."+ag);ah=ah||function(){ad.request_draw({clear_tile_cache:true})};if(ae.length!==0){ae.text(ad.prefs[ac])}else{ae=$("<div/>").text(ad.prefs[ac]).make_text_editable({num_cols:12,on_finish:function(aj){$(".tooltip").remove();ad.config.set_param_value(ac,aj);ah()},help_text:"Set "+ai+" value"}).addClass("yaxislabel "+ag).css("color",this.prefs.label_color);this.container_div.prepend(ae)}},postdraw_actions:function(af,ag,ai,ac){var ae=ab.filter(af,function(aj){return(aj instanceof M)});if(ae.length>0){this.max_height_px=0;var ad=this;ab.each(af,function(aj){if(!(aj instanceof M)){aj.html_elt.remove();ad.draw_helper(aj.region,ai,{force:true,mode:"Coverage"})}});ad._add_yaxis_label("max")}else{this.container_div.find(".yaxislabel").remove();var ah=ab.find(af,function(aj){return aj.has_icons});if(ah){ab.each(af,function(aj){if(!aj.has_icons){aj.html_elt.css("padding-top",F)}})}}},get_mode:function(ac){return this.mode},update_auto_mode:function(ac){},_get_drawables:function(){return[this]},draw_helper:function(al,an,ao){if(!ao){ao={}}var ad=ao.force,ai=ao.mode||this.mode,af=1/an,ae=this,ag=this._get_drawables(),am=this._gen_tile_cache_key(an,al),ah=function(ap){return(ap&&"track" in ap)};var aj=(ad?undefined:ae.tile_cache.get_elt(am));if(aj){if(ah(aj)){ae.show_tile(aj,an)}return aj}if(ao.data_fetch===false){return null}var ak=function(){var ap=(ab.find(C,function(ar){return ar===ai})?"Coverage":ai);var aq=ab.map(ag,function(ar){return ar.data_manager.get_data(al,ap,af,ae.data_url_extra_params)});if(view.reference_track){aq.push(view.reference_track.data_manager.get_data(al,ai,af,view.reference_track.data_url_extra_params))}return aq};var ac=$.Deferred();ae.tile_cache.set_elt(am,ac);$.when.apply($,ak()).then(function(){var ap=ak(),av=ap,aB;if(view.reference_track){aB=view.reference_track.data_manager.subset_entry(ap.pop(),al)}var aw=[],at=[];ab.each(ag,function(aG,aD){var aF=aG.mode,aE=av[aD];if(aF==="Auto"){aF=aG.get_mode(aE);aG.update_auto_mode(aF)}aw.push(aF);at.push(aG.get_canvas_height(aE,aF,an,aq))});var au=ae.view.canvas_manager.new_canvas(),ax=al.get("start"),aC=al.get("end"),ar=0,aq=Math.ceil((aC-ax)*an)+ae.left_offset,az=ab.max(at),ay;au.width=aq;au.height=(ao.height||az);var aA=au.getContext("2d");aA.translate(ae.left_offset,0);if(ag.length>1){aA.globalAlpha=0.5;aA.globalCompositeOperation="source-over"}ab.each(ag,function(aE,aD){ay=aE.draw_tile(av[aD],aA,aw[aD],al,an,aB)});if(ay!==undefined){ae.tile_cache.set_elt(am,ay);ae.show_tile(ay,an)}ac.resolve(ay)});return ac},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_line_track_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.LinePainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new M(this,ag,ai,af,ac.data)},draw_tile:function(ac,ad,ag,af,ah,ae){},show_tile:function(ae,ah){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ah;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{this.tiles_div.append(ac)}this.max_height_px=Math.max(this.max_height_px,$(ae.canvas).height());ac.parent().children().css("height",this.max_height_px+"px");var af=this.max_height_px;if(this.visible_height_px!==0){af=Math.min(this.max_height_px,this.visible_height_px)}this.tiles_div.css("height",af+"px")},tool_region_and_parameters_str:function(af){var ac=this,ae=(af!==undefined?af.toString():"all"),ad=ab.values(ac.tool.get_inputs_dict()).join(", ");return" - region=["+ae+"], parameters=["+ad+"]"},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="bigwig"}else{if(ac.dataset_type==="bigwig"||ac.extra_info==="no_detail"){return false}else{return true}}}},can_subset:function(ac){if(ac.message||ac.extra_info==="no_detail"){return false}else{if(ac.dataset_type==="bigwig"){return(ac.data[1][0]-ac.data[0][0]===1)}}return true},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state"}});var W=function(ad,ac){var ae={resize:false};g.call(this,ad,ac,ae);this.container_div.addClass("label-track")};q(W.prototype,g.prototype,{build_header_div:function(){},init:function(){this.enabled=true},predraw_init:function(){},_draw:function(ag){var ae=this.view,af=ae.high-ae.low,aj=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/aj)*aj,ah=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ai=(ac-ae.low)/af*ah;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ai-1}));ac+=aj}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){N.call(this,ad,ac,ag);this.drawables=[];if("drawables" in ag){var af;for(var ae=0;ae<ag.drawables.length;ae++){af=ag.drawables[ae];this.drawables[ae]=p(af,ad,null);if(af.left_offset>this.left_offset){this.left_offset=af.left_offset}}this.enabled=true}ab.each(this.drawables,function(ah){if(ah instanceof d||ah instanceof T){ah.change_mode("Coverage")}});this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,N.prototype,{display_modes:C,action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".tooltip").remove();ac.show_group()}}].concat(N.prototype.action_icons_def),to_dict:A.prototype.to_dict,add_drawable:A.prototype.add_drawable,unpack_drawables:A.prototype.unpack_drawables,change_mode:function(ac){N.prototype.change_mode.call(this,ac);for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].change_mode(ac)}},init:function(){var ae=[];for(var ad=0;ad<this.drawables.length;ad++){ae.push(this.drawables[ad].init())}var ac=this;$.when.apply($,ae).then(function(){ac.enabled=true;ac.request_draw()})},update_icons:function(){this.action_icons.filters_icon.hide();this.action_icons.tools_icon.hide();this.action_icons.param_space_viz_icon.hide()},can_draw:r.prototype.can_draw,_get_drawables:function(){return this.drawables},show_group:function(){var af=new P(this.view,this.container,{name:this.prefs.name}),ac;for(var ae=0;ae<this.drawables.length;ae++){ac=this.drawables[ae];ac.update_icons();af.add_drawable(ac);ac.container=af;af.content_div.append(ac.container_div)}var ad=this.container.replace_drawable(this,af,true);af.request_draw({clear_tile_cache:true})},before_draw:function(){N.prototype.before_draw.call(this);var ad=ab.min(ab.map(this.drawables,function(ae){return ae.prefs.min_value})),ac=ab.max(ab.map(this.drawables,function(ae){return ae.prefs.max_value}));this.prefs.min_value=ad;this.prefs.max_value=ac;ab.each(this.drawables,function(ae){ae.prefs.min_value=ad;ae.prefs.max_value=ac})},update_all_min_max:function(){var ac=this;ab.each(this.drawables,function(ad){ad.prefs.min_value=ac.prefs.min_value;ad.prefs.max_value=ac.prefs.max_value});this.request_draw({clear_tile_cache:true})},postdraw_actions:function(ai,ac,al,ah){N.prototype.postdraw_actions.call(this,ai,ac,al,ah);var ag=-1,ae;for(ae=0;ae<ai.length;ae++){var aj=ai[ae].html_elt.find("canvas").height();if(aj>ag){ag=aj}}for(ae=0;ae<ai.length;ae++){var af=ai[ae];if(af.html_elt.find("canvas").height()!==ag){this.draw_helper(af.region,al,{force:true,height:ag});af.html_elt.remove()}}var ad=this,ak=function(){ad.update_all_min_max()};this._add_yaxis_label("min",ak);this._add_yaxis_label("max",ak)}});var D=function(ac){N.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});this.left_offset=ac.canvas_manager.char_width_px;this.container_div.addClass("reference-track");this.data_url=galaxy_config.root+"api/genomes/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new y.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(D.prototype,r.prototype,N.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"height",type:"int",default_value:13,hidden:true}]),build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},predraw_init:function(){},can_draw:r.prototype.can_draw,draw_helper:function(ad,ae,ac){if(ae>this.view.canvas_manager.char_width_px){this.tiles_div.show();return N.prototype.draw_helper.call(this,ad,ae,ac)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(ae,ak,af,ah,al){var ad=this.data_manager.subset_entry(ae,ah),aj=ad.data;var ac=ak.canvas;ak.font=ak.canvas.manager.default_font;ak.textAlign="center";for(var ag=0,ai=aj.length;ag<ai;ag++){ak.fillStyle=this.view.get_base_color(aj[ag]);ak.fillText(aj[ag],Math.floor(ag*al),10)}return new c(this,ah,al,ac,ad)}});var h=function(ad,ac,ae){this.mode="Histogram";N.call(this,ad,ac,ae)};q(h.prototype,r.prototype,N.prototype,{display_modes:C,config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Color",type:"color",default_value:l.get_random_color()},{key:"min_value",label:"Min Value",type:"float",default_value:undefined},{key:"max_value",label:"Max Value",type:"float",default_value:undefined},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:30,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},before_draw:function(){},draw_tile:function(ac,ad,af,ae,ag){return this._draw_line_track_tile(ac,ad,af,ae,ag)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)},postdraw_actions:function(ad,ae,af,ac){this._add_yaxis_label("max");this._add_yaxis_label("min")}});var t=function(ad,ac,ae){this.mode="Heatmap";N.call(this,ad,ac,ae)};q(t.prototype,r.prototype,N.prototype,{display_modes:["Heatmap"],config_params:ab.union(r.prototype.config_params,[{key:"pos_color",label:"Positive Color",type:"color",default_value:"#FF8C00"},{key:"neg_color",label:"Negative Color",type:"color",default_value:"#4169E1"},{key:"min_value",label:"Min Value",type:"float",default_value:-1},{key:"max_value",label:"Max Value",type:"float",default_value:1},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:500,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,ae,ah,ag,ai){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah);ad.draw(ae,af.width,af.height,ai);return new c(this,ag,ai,af,ac.data)}});var d=function(ad,ac,ae){N.call(this,ad,ac,ae);this.container_div.addClass("feature-track");this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(d.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true,help:"Show the number of items in each bin when drawing summary histogram"},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"connector_style",label:"Connector style",type:"select",default_value:"fishbones",options:[{label:"Line with arrows",value:"fishbone"},{label:"Arcs",value:"arcs"}]},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.set_painter_from_config();this.request_draw({clear_tile_cache:true})},set_painter_from_config:function(){if(this.config.get("values").connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},postdraw_actions:function(am,ae,an,al){N.prototype.postdraw_actions.call(this,am,ae,an,al);var ag=this,ah;if(ag.filters_manager){var af=ag.filters_manager.filters,aj;for(aj=0;aj<af.length;aj++){af[aj].update_ui_elt()}var ai=false,ak,ad;for(ah=0;ah<am.length;ah++){if(am[ah].data.length){ak=am[ah].data[0];for(aj=0;aj<af.length;aj++){ad=af[aj];if(ad.applies_to(ak)&&ad.min!==ad.max){ai=true;break}}}}if(ag.filters_available!==ai){ag.filters_available=ai;if(!ag.filters_available){ag.filters_manager.hide()}ag.update_icons()}}if(am[0] instanceof O){var ac=true;for(ah=0;ah<am.length;ah++){if(!am[ah].all_slotted){ac=false;break}}if(!ac){this.action_icons.show_more_rows_icon.show()}else{this.action_icons.show_more_rows_icon.hide()}}else{this.action_icons.show_more_rows_icon.hide()}},update_auto_mode:function(ac){if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}this.action_icons.mode_icon.attr("title","Set display mode (now: Auto/"+ac+")")}},incremental_slots:function(ag,ac,af){var ad=this.view.canvas_manager.dummy_context,ae=this.slotters[ag];if(!ae||(ae.mode!==af)){ae=new (u.FeatureSlotter)(ag,af,B,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.extra_info==="no_detail"||this.is_overview){mode="no_detail"}else{if(this.view.high-this.view.low>I){mode="Squish"}else{mode="Pack"}}return mode},get_canvas_height:function(ac,ag,ah,ad){if(ag==="Coverage"||ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var af=this.incremental_slots(ah,ac.data,ag);var ae=new (this.painter)(null,null,null,this.prefs,ag);return Math.max(this.min_height_px,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,af,aj,ae){var ap=this,ad=aq.canvas,ax=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(am.dataset_type==="bigwig"){return this._draw_line_track_tile(am,aq,ao,af,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var ar=0,au=am.data.length;ar<au;ar++){var ah=am.data[ar];var at=false;var al;for(var aw=0,aB=ak.length;aw<aB;aw++){al=ak[aw];al.update_attrs(ah);if(!al.keep(ah)){at=true;break}}if(!at){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aA=(this.filters_manager.alpha_filter?new E(this.filters_manager.alpha_filter):null),ay=(this.filters_manager.height_filter?new E(this.filters_manager.height_filter):null),az=new (this.painter)(ai,ax,ac,this.prefs,ao,aA,ay,ae,function(aC){return ap.view.get_base_color(aC)});var av=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){av=az.draw(aq,ad.width,ad.height,aj,an);av.translation=-ag}return new O(ap,af,aj,ad,am.data,ao,am.message,all_slotted,av)}});var Z=function(ad,ac,ae){N.call(this,ad,ac,ae);this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,N.prototype,{display_modes:["Auto","Coverage","Dense","Squish","Pack"],config_params:ab.union(r.prototype.config_params,[{key:"color",label:"Histogram color",type:"color",default_value:l.get_random_color()},{key:"show_sample_data",label:"Show sample data",type:"bool",default_value:true},{key:"show_labels",label:"Show summary and sample labels",type:"bool",default_value:true},{key:"summary_height",label:"Locus summary height",type:"float",default_value:20},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})},draw_tile:function(ac,af,ah,ag,ai){if(ac.dataset_type==="bigwig"){return this._draw_line_track_tile(ac,af,"Histogram",ag,ai)}else{var ae=this.view,ad=new (this.painter)(ac.data,ag.get("start"),ag.get("end"),this.prefs,ah,function(aj){return ae.get_base_color(aj)});ad.draw(af,af.canvas.width,af.canvas.height,ai);return new c(this,ag,ai,af.canvas,ac.data)}},get_canvas_height:function(ac,ag,ah,ae){if(ac.dataset_type==="bigwig"){return this.summary_draw_height}else{var ad=(this.dataset.get_metadata("sample_names")?this.dataset.get_metadata("sample_names").length:0);if(ad===0&&ac.data.length!==0){ad=ac.data[0][7].match(/,/g);if(ad===null){ad=1}else{ad=ad.length+1}}var af=new (this.painter)(null,null,null,this.prefs,ag);return af.get_required_height(ad)}},predraw_init:function(){var ac=[g.prototype.predraw_init.call(this)];if(!this.dataset.get_metadata("sample_names")){ac.push(this.dataset.fetch())}return ac},postdraw_actions:function(ag,ah,aj,ad){N.prototype.postdraw_actions.call(this,ag,ah,aj,ad);var af=ab.filter(ag,function(ak){return(ak instanceof M)});var ae=this.dataset.get_metadata("sample_names");if(af.length===0&&this.prefs.show_labels&&ae){var ac;if(this.container_div.find(".yaxislabel.variant").length===0){ac=this.prefs.summary_height/2;this.tiles_div.prepend($("<div/>").text("Summary").addClass("yaxislabel variant top").css({"font-size":ac+"px",top:(this.prefs.summary_height-ac)/2+"px"}));if(this.prefs.show_sample_data){var ai=ae.join("<br/>");this.tiles_div.prepend($("<div/>").html(ai).addClass("yaxislabel variant top sample").css({top:this.prefs.summary_height+2,}))}}ac=(this.mode==="Squish"?5:10)+"px";$(this.tiles_div).find(".sample").css({"font-size":ac,"line-height":ac});$(this.tiles_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel.variant").remove()}}});var T=function(ad,ac,ae){d.call(this,ad,ac,ae);this.painter=(ad.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(T.prototype,r.prototype,N.prototype,d.prototype,{config_params:ab.union(r.prototype.config_params,[{key:"block_color",label:"Block and sense strand color",type:"color",default_value:l.get_random_color()},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:l.get_random_color()},{key:"label_color",label:"Label color",type:"color",default_value:"black"},{key:"show_insertions",label:"Show insertions",type:"bool",default_value:false},{key:"show_differences",label:"Show differences only",type:"bool",default_value:true},{key:"show_counts",label:"Show summary counts",type:"bool",default_value:true},{key:"mode",type:"string",default_value:this.mode,hidden:true},{key:"min_value",label:"Histogram minimum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"max_value",label:"Histogram maximum",type:"float",default_value:null,help:"clear value to set automatically"},{key:"height",type:"int",default_value:0,hidden:true}]),config_onchange:function(){this.set_name(this.prefs.name);this.request_draw({clear_tile_cache:true})}});var e={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:d,LineTrack:h,ReadTrack:T,VariantTrack:Z,VcfTrack:Z};var p=function(ae,ad,ac){if("copy" in ae){return ae.copy(ac)}else{var af=ae.obj_type;if(!af){af=ae.track_type}return new e[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:d,DiagonalHeatmapTrack:t,ReadTrack:T,VariantTrack:Z,CompositeTrack:f,object_from_template:p}});
\ No newline at end of file
https://bitbucket.org/galaxy/galaxy-central/commits/04225eb28389/
Changeset: 04225eb28389
User: jgoecks
Date: 2013-10-22 00:42:04
Summary: Automated merge of next-stable
Affected #: 0 files
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.
1
0
9 new commits in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/0eafcb644470/
Changeset: 0eafcb644470
Branch: next-stable
User: dannon
Date: 2013-10-21 22:23:43
Summary: Strip unused data_provider_registry
Affected #: 1 file
diff -r 81880a04e6e79d944a6d9c225b36417114cd38ec -r 0eafcb6444701fb40339ee6918a3d33fdf4a0479 lib/galaxy/webapps/galaxy/api/datasets.py
--- a/lib/galaxy/webapps/galaxy/api/datasets.py
+++ b/lib/galaxy/webapps/galaxy/api/datasets.py
@@ -101,7 +101,6 @@
# If there is a chrom, check for data on the chrom.
if chrom:
- data_provider_registry = trans.app.data_provider_registry
data_provider = trans.app.data_provider_registry.get_data_provider( trans,
original_dataset=dataset, source='index' )
if not data_provider.has_data( chrom ):
https://bitbucket.org/galaxy/galaxy-central/commits/86912262ab6f/
Changeset: 86912262ab6f
Branch: next-stable
User: dannon
Date: 2013-10-21 22:40:30
Summary: Expose dataset api anonymously -- this reflects the behavior one expects in the web interface, delegating permission enforcement to the backend
Affected #: 1 file
diff -r 0eafcb6444701fb40339ee6918a3d33fdf4a0479 -r 86912262ab6f47a9019556731940d0cde19f7b99 lib/galaxy/webapps/galaxy/api/datasets.py
--- a/lib/galaxy/webapps/galaxy/api/datasets.py
+++ b/lib/galaxy/webapps/galaxy/api/datasets.py
@@ -23,7 +23,7 @@
trans.response.status = 501
return 'not implemented'
- @web.expose_api
+ @web.expose_api_anonymous
def show( self, trans, id, hda_ldda='hda', data_type=None, provider=None, **kwd ):
"""
GET /api/datasets/{encoded_dataset_id}
@@ -243,7 +243,7 @@
return data
- @web.expose_api_raw
+ @web.expose_api_raw_anonymous
def display( self, trans, history_content_id, history_id,
preview=False, filename=None, to_ext=None, chunk=None, **kwd ):
"""
https://bitbucket.org/galaxy/galaxy-central/commits/bf169fb107cc/
Changeset: bf169fb107cc
Branch: next-stable
User: dannon
Date: 2013-10-21 22:41:04
Summary: Add decorator for exposing via the api both anonymously and raw -- to be refactored later
Affected #: 1 file
diff -r 86912262ab6f47a9019556731940d0cde19f7b99 -r bf169fb107cc441fbefbf01544764d87fa6e2af1 lib/galaxy/web/framework/__init__.py
--- a/lib/galaxy/web/framework/__init__.py
+++ b/lib/galaxy/web/framework/__init__.py
@@ -110,6 +110,14 @@
"""
return expose_api( func, to_json=False )
+#DBTODO refactor these post-dist.
+def expose_api_raw_anonymous( func ):
+ """
+ Expose this function via the API but don't dump the results
+ to JSON.
+ """
+ return expose_api( func, to_json=False, user_required=False )
+
def expose_api_anonymous( func, to_json=True ):
"""
Expose this function via the API but don't require a set user.
https://bitbucket.org/galaxy/galaxy-central/commits/e9a6c1738ffc/
Changeset: e9a6c1738ffc
Branch: next-stable
User: dannon
Date: 2013-10-21 23:31:09
Summary: Add expose_api_raw_anonymous to galaxy/web package
Affected #: 1 file
diff -r bf169fb107cc441fbefbf01544764d87fa6e2af1 -r e9a6c1738ffc3dab035f5c2eb01b99c57fe77aa5 lib/galaxy/web/__init__.py
--- a/lib/galaxy/web/__init__.py
+++ b/lib/galaxy/web/__init__.py
@@ -13,4 +13,5 @@
from framework import expose_api
from framework import expose_api_anonymous
from framework import expose_api_raw
+from framework import expose_api_raw_anonymous
from framework.base import httpexceptions
https://bitbucket.org/galaxy/galaxy-central/commits/902bf096a4aa/
Changeset: 902bf096a4aa
User: dannon
Date: 2013-10-21 23:31:50
Summary: Merge next-stable to default
Affected #: 3 files
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 902bf096a4aa1be446676d178ac5f6db4e5b558f lib/galaxy/web/__init__.py
--- a/lib/galaxy/web/__init__.py
+++ b/lib/galaxy/web/__init__.py
@@ -13,4 +13,5 @@
from framework import expose_api
from framework import expose_api_anonymous
from framework import expose_api_raw
+from framework import expose_api_raw_anonymous
from framework.base import httpexceptions
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 902bf096a4aa1be446676d178ac5f6db4e5b558f lib/galaxy/web/framework/__init__.py
--- a/lib/galaxy/web/framework/__init__.py
+++ b/lib/galaxy/web/framework/__init__.py
@@ -110,6 +110,14 @@
"""
return expose_api( func, to_json=False )
+#DBTODO refactor these post-dist.
+def expose_api_raw_anonymous( func ):
+ """
+ Expose this function via the API but don't dump the results
+ to JSON.
+ """
+ return expose_api( func, to_json=False, user_required=False )
+
def expose_api_anonymous( func, to_json=True ):
"""
Expose this function via the API but don't require a set user.
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 902bf096a4aa1be446676d178ac5f6db4e5b558f lib/galaxy/webapps/galaxy/api/datasets.py
--- a/lib/galaxy/webapps/galaxy/api/datasets.py
+++ b/lib/galaxy/webapps/galaxy/api/datasets.py
@@ -23,7 +23,7 @@
trans.response.status = 501
return 'not implemented'
- @web.expose_api
+ @web.expose_api_anonymous
def show( self, trans, id, hda_ldda='hda', data_type=None, provider=None, **kwd ):
"""
GET /api/datasets/{encoded_dataset_id}
@@ -101,7 +101,6 @@
# If there is a chrom, check for data on the chrom.
if chrom:
- data_provider_registry = trans.app.data_provider_registry
data_provider = trans.app.data_provider_registry.get_data_provider( trans,
original_dataset=dataset, source='index' )
if not data_provider.has_data( chrom ):
@@ -244,7 +243,7 @@
return data
- @web.expose_api_raw
+ @web.expose_api_raw_anonymous
def display( self, trans, history_content_id, history_id,
preview=False, filename=None, to_ext=None, chunk=None, **kwd ):
"""
https://bitbucket.org/galaxy/galaxy-central/commits/bb8975aafcd9/
Changeset: bb8975aafcd9
User: dannon
Date: 2013-10-21 23:32:06
Summary: Merge with central
Affected #: 29 files
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce lib/galaxy/web/base/controller.py
--- a/lib/galaxy/web/base/controller.py
+++ b/lib/galaxy/web/base/controller.py
@@ -633,11 +633,11 @@
# if a tool declares 'force_history_refresh' in its xml, when the hda -> ready, reload the history panel
# expensive
- if( ( hda.state in [ 'running', 'queued' ] )
- and ( hda.creating_job and hda.creating_job.tool_id ) ):
- tool_used = trans.app.toolbox.get_tool( hda.creating_job.tool_id )
- if tool_used and tool_used.force_history_refresh:
- hda_dict[ 'force_history_refresh' ] = True
+ #if( ( hda.state in [ 'running', 'queued' ] )
+ #and ( hda.creating_job and hda.creating_job.tool_id ) ):
+ # tool_used = trans.app.toolbox.get_tool( hda.creating_job.tool_id )
+ # if tool_used and tool_used.force_history_refresh:
+ # hda_dict[ 'force_history_refresh' ] = True
return trans.security.encode_dict_ids( hda_dict )
@@ -653,13 +653,14 @@
'accessible': False
})
- def get_hda_dict_with_error( self, trans, hda, error_msg='' ):
+ def get_hda_dict_with_error( self, trans, hda=None, history_id=None, id=None, error_msg='Error' ):
return trans.security.encode_dict_ids({
- 'id' : hda.id,
- 'history_id': hda.history.id,
- 'hid' : hda.hid,
- 'name' : hda.name,
- 'error' : error_msg
+ 'id' : hda.id if hda else id,
+ 'history_id': hda.history.id if hda else history_id,
+ 'hid' : hda.hid if hda else '(unknown)',
+ 'name' : hda.name if hda else '(unknown)',
+ 'error' : error_msg,
+ 'state' : trans.model.Dataset.states.NEW
})
def get_display_apps( self, trans, hda ):
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce lib/galaxy/webapps/galaxy/api/histories.py
--- a/lib/galaxy/webapps/galaxy/api/histories.py
+++ b/lib/galaxy/webapps/galaxy/api/histories.py
@@ -97,6 +97,9 @@
# Most recent active history for user sessions, not deleted
history = trans.user.galaxy_sessions[0].histories[-1].history
+ elif history_id == "current":
+ history = trans.get_history( create=True )
+
else:
history = self.get_history( trans, history_id, check_ownership=False,
check_accessible=True, deleted=deleted )
@@ -110,7 +113,7 @@
except Exception, e:
msg = "Error in history API at showing history detail: %s" % ( str( e ) )
- log.exception( msg, exc_info=True )
+ log.exception( e )
trans.response.status = 500
return msg
@@ -174,7 +177,8 @@
trans.sa_session.add( new_history )
trans.sa_session.flush()
- item = new_history.to_dict(view='element', value_mapper={'id':trans.security.encode_id})
+ #item = new_history.to_dict(view='element', value_mapper={'id':trans.security.encode_id})
+ item = self.get_history_dict( trans, new_history )
item['url'] = url_for( 'history', id=item['id'] )
#TODO: possibly default to True here - but favor explicit for now (and backwards compat)
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce lib/galaxy/webapps/galaxy/api/history_contents.py
--- a/lib/galaxy/webapps/galaxy/api/history_contents.py
+++ b/lib/galaxy/webapps/galaxy/api/history_contents.py
@@ -59,22 +59,21 @@
encoded_hda_id = trans.security.encode_id( hda.id )
if encoded_hda_id in ids:
#TODO: share code with show
- try:
- hda_dict = self.get_hda_dict( trans, hda )
- hda_dict[ 'display_types' ] = self.get_old_display_applications( trans, hda )
- hda_dict[ 'display_apps' ] = self.get_display_apps( trans, hda )
- rval.append( hda_dict )
-
- except Exception, exc:
- # don't fail entire list if hda err's, record and move on
- log.error( "Error in history API at listing contents with history %s, hda %s: (%s) %s",
- history_id, encoded_hda_id, type( exc ), str( exc ), exc_info=True )
- rval.append( self.get_hda_dict_with_error( trans, hda, str( exc ) ) )
+ rval.append( self._detailed_hda_dict( trans, hda ) )
# if no ids passed, return a _SUMMARY_ of _all_ datasets in the history
else:
+ details = kwd.get( 'details', None ) or []
+ if details and details != 'all':
+ details = util.listify( details )
+
for hda in history.datasets:
- rval.append( self._summary_hda_dict( trans, history_id, hda ) )
+ encoded_hda_id = trans.security.encode_id( hda.id )
+ if( ( encoded_hda_id in details )
+ or ( details == 'all' ) ):
+ rval.append( self._detailed_hda_dict( trans, hda ) )
+ else:
+ rval.append( self._summary_hda_dict( trans, history_id, hda ) )
except Exception, e:
# for errors that are not specific to one hda (history lookup or summary list)
@@ -85,7 +84,7 @@
return rval
#TODO: move to model or Mixin
- def _summary_hda_dict( self, trans, history_id, hda ):
+ def _summary_hda_dict( self, trans, encoded_history_id, hda ):
"""
Returns a dictionary based on the HDA in summary form::
{
@@ -99,11 +98,32 @@
encoded_id = trans.security.encode_id( hda.id )
return {
'id' : encoded_id,
+ 'history_id' : encoded_history_id,
'name' : hda.name,
'type' : api_type,
- 'url' : url_for( 'history_content', history_id=history_id, id=encoded_id, ),
+ 'state' : hda.state,
+ 'deleted': hda.deleted,
+ 'visible': hda.visible,
+ 'hid' : hda.hid,
+ 'url' : url_for( 'history_content', history_id=encoded_history_id, id=encoded_id, ),
}
+ def _detailed_hda_dict( self, trans, hda ):
+ """
+ Detailed dictionary of hda values.
+ """
+ try:
+ hda_dict = self.get_hda_dict( trans, hda )
+ hda_dict[ 'display_types' ] = self.get_old_display_applications( trans, hda )
+ hda_dict[ 'display_apps' ] = self.get_display_apps( trans, hda )
+ return hda_dict
+
+ except Exception, exc:
+ # catch error here - returning a briefer hda_dict with an error attribute
+ log.exception( "Error in history API at listing contents with history %s, hda %s: (%s) %s",
+ hda.history_id, hda.id, type( exc ), str( exc ) )
+ return self.get_hda_dict_with_error( trans, hda=hda, error_msg=str( exc ) )
+
@web.expose_api_anonymous
def show( self, trans, id, history_id, **kwd ):
"""
@@ -244,7 +264,7 @@
trans.response.status = 501
return
- @web.expose_api
+ @web.expose_api_anonymous
def update( self, trans, history_id, id, payload, **kwd ):
"""
update( self, trans, history_id, id, payload, **kwd )
@@ -269,10 +289,28 @@
#TODO: PUT /api/histories/{encoded_history_id} payload = { rating: rating } (w/ no security checks)
changed = {}
try:
- hda = self.get_dataset( trans, id,
- check_ownership=True, check_accessible=True, check_state=True )
- # validation handled here and some parsing, processing, and conversion
- payload = self._validate_and_parse_update_payload( payload )
+ # anon user
+ if trans.user == None:
+ if history_id != trans.security.encode_id( trans.history.id ):
+ trans.response.status = 401
+ return { 'error': 'Anonymous users cannot edit histories other than their current history' }
+
+ anon_allowed_payload = {}
+ if 'deleted' in payload:
+ anon_allowed_payload[ 'deleted' ] = payload[ 'deleted' ]
+ if 'visible' in payload:
+ anon_allowed_payload[ 'visible' ] = payload[ 'visible' ]
+
+ payload = self._validate_and_parse_update_payload( anon_allowed_payload )
+ hda = self.get_dataset( trans, id, check_ownership=False, check_accessible=False, check_state=True )
+ if hda.history != trans.history:
+ trans.response.status = 401
+ return { 'error': 'Anonymous users cannot edit datasets outside their current history' }
+
+ else:
+ payload = self._validate_and_parse_update_payload( payload )
+ hda = self.get_dataset( trans, id, check_ownership=True, check_accessible=True, check_state=True )
+
# additional checks here (security, etc.)
changed = self.set_hda_from_dict( trans, hda, payload )
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce lib/galaxy/webapps/galaxy/controllers/root.py
--- a/lib/galaxy/webapps/galaxy/controllers/root.py
+++ b/lib/galaxy/webapps/galaxy/controllers/root.py
@@ -5,7 +5,7 @@
import os
import urllib
-from paste.httpexceptions import HTTPNotFound
+from paste.httpexceptions import HTTPNotFound, HTTPBadGateway
from galaxy import web
from galaxy.web import url_for
@@ -30,7 +30,8 @@
@web.expose
def index(self, trans, id=None, tool_id=None, mode=None, workflow_id=None, m_c=None, m_a=None, **kwd):
- """Called on the root url to display the main Galaxy page.
+ """
+ Called on the root url to display the main Galaxy page.
"""
return trans.fill_template( "root/index.mako",
tool_id=tool_id,
@@ -99,63 +100,75 @@
show_deleted=string_as_bool( show_deleted ),
show_hidden=string_as_bool( show_hidden ) )
- @web.expose
- def history( self, trans, as_xml=False, show_deleted=None, show_hidden=None, hda_id=None, **kwd ):
- """Display the current history, creating a new history if necessary.
-
- NOTE: No longer accepts "id" or "template" options for security reasons.
- """
- if as_xml:
- return self.history_as_xml( trans,
- show_deleted=string_as_bool( show_deleted ), show_hidden=string_as_bool( show_hidden ) )
-
- # get all datasets server-side, client-side will get flags and render appropriately
- show_deleted = string_as_bool_or_none( show_deleted )
- show_purged = show_deleted
- show_hidden = string_as_bool_or_none( show_hidden )
- params = Params( kwd )
- message = params.get( 'message', '' )
- #TODO: ugh...
- message = message if message != 'None' else ''
- status = params.get( 'status', 'done' )
-
- if trans.app.config.require_login and not trans.user:
- return trans.fill_template( '/no_access.mako', message = 'Please log in to access Galaxy histories.' )
-
- def err_msg( where=None ):
- where = where if where else 'getting the history data from the server'
- err_msg = ( 'An error occurred %s. '
- + 'Please contact a Galaxy administrator if the problem persists.' ) %( where )
- return err_msg, 'error'
-
+ def _get_current_history_data( self, trans ):
history_dictionary = {}
hda_dictionaries = []
+
try:
history = trans.get_history( create=True )
hdas = self.get_history_datasets( trans, history,
show_deleted=True, show_hidden=True, show_purged=True )
for hda in hdas:
+ hda_dict = {}
try:
- hda_dictionaries.append( self.get_hda_dict( trans, hda ) )
+ hda_dict = self.get_hda_dict( trans, hda )
except Exception, exc:
# don't fail entire list if hda err's, record and move on
log.error( 'Error bootstrapping hda %d: %s', hda.id, str( exc ), exc_info=True )
- hda_dictionaries.append( self.get_hda_dict_with_error( trans, hda, str( exc ) ) )
+ hda_dict = self.get_hda_dict_with_error( trans, hda, str( exc ) )
+
+ hda_dictionaries.append( hda_dict )
# re-use the hdas above to get the history data...
history_dictionary = self.get_history_dict( trans, history, hda_dictionaries=hda_dictionaries )
except Exception, exc:
user_id = str( trans.user.id ) if trans.user else '(anonymous)'
- log.error( 'Error bootstrapping history for user %s: %s', user_id, str( exc ), exc_info=True )
- message, status = err_msg()
+ log.exception( 'Error bootstrapping history for user %s: %s', user_id, str( exc ) )
+ message = ( 'An error occurred getting the history data from the server. '
+ + 'Please contact a Galaxy administrator if the problem persists.' )
history_dictionary[ 'error' ] = message
- return trans.stream_template_mako( "root/history.mako",
- history_json = to_json_string( history_dictionary ), hda_json = to_json_string( hda_dictionaries ),
- show_deleted=show_deleted, show_hidden=show_hidden, hda_id=hda_id, log=log, message=message, status=status )
+ return {
+ 'history' : history_dictionary,
+ 'hdas' : hda_dictionaries
+ }
+
+ @web.expose
+ def history( self, trans, as_xml=False, show_deleted=None, show_hidden=None, **kwd ):
+ """
+ Display the current history in it's own page or as xml.
+ """
+ if as_xml:
+ return self.history_as_xml( trans,
+ show_deleted=string_as_bool( show_deleted ), show_hidden=string_as_bool( show_hidden ) )
+
+ if trans.app.config.require_login and not trans.user:
+ return trans.fill_template( '/no_access.mako', message = 'Please log in to access Galaxy histories.' )
+
+ # get all datasets server-side, client-side will get flags and render appropriately
+ show_deleted = string_as_bool_or_none( show_deleted )
+ show_purged = show_deleted
+ show_hidden = string_as_bool_or_none( show_hidden )
+
+ history_dictionary = {}
+ hda_dictionaries = []
+ try:
+ history_data = self._get_current_history_data( trans )
+ history_dictionary = history_data[ 'history' ]
+ hda_dictionaries = history_data[ 'hdas' ]
+
+ except Exception, exc:
+ user_id = str( trans.user.id ) if trans.user else '(anonymous)'
+ log.exception( 'Error bootstrapping history for user %s: %s', user_id, str( exc ) )
+ history_dictionary[ 'error' ] = ( 'An error occurred getting the history data from the server. '
+ + 'Please contact a Galaxy administrator if the problem persists.' )
+
+ return trans.fill_template_mako( "root/history.mako",
+ history = history_dictionary, hdas = hda_dictionaries,
+ show_deleted=show_deleted, show_hidden=show_hidden )
## ---- Dataset display / editing ----------------------------------------
@web.expose
@@ -503,7 +516,22 @@
return rval
@web.expose
- def generate_error( self, trans ):
+ def generate_error( self, trans, code=500 ):
"""Raises an exception (debugging).
"""
+ trans.response.status = code
raise Exception( "Fake error!" )
+
+ @web.json
+ def generate_json_error( self, trans, code=500 ):
+ """Raises an exception (debugging).
+ """
+ try:
+ code = int( code )
+ except Exception, exc:
+ code = 500
+
+ if code == 502:
+ raise HTTPBadGateway()
+ trans.response.status = code
+ return { 'error': 'Fake error!' }
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce lib/galaxy/webapps/galaxy/controllers/tool_runner.py
--- a/lib/galaxy/webapps/galaxy/controllers/tool_runner.py
+++ b/lib/galaxy/webapps/galaxy/controllers/tool_runner.py
@@ -325,4 +325,5 @@
<p><b>Please do not use your browser\'s "stop" or "reload" buttons until the upload is complete, or it may be interrupted.</b></p><p>You may safely continue to use Galaxy while the upload is in progress. Using "stop" and "reload" on pages other than Galaxy is also safe.</p>
"""
+ #return trans.show_message( msg, refresh_frames=[ 'history' ] )
return trans.show_message( msg )
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce static/scripts/mvc/base-mvc.js
--- a/static/scripts/mvc/base-mvc.js
+++ b/static/scripts/mvc/base-mvc.js
@@ -7,31 +7,30 @@
name: null,
hidden: false
},
-
+
show: function() {
this.set("hidden", false);
},
-
+
hide: function() {
this.set("hidden", true);
},
-
+
is_visible: function() {
return !this.attributes.hidden;
}
});
-
/**
* Base view that handles visibility based on model's hidden attribute.
*/
var BaseView = Backbone.View.extend({
-
+
initialize: function() {
this.model.on("change:hidden", this.update_visible, this);
this.update_visible();
},
-
+
update_visible: function() {
if( this.model.attributes.hidden ){
this.$el.hide();
@@ -120,7 +119,8 @@
// ~constants for the current engine
var STORAGE_ENGINE = sessionStorage,
STORAGE_ENGINE_GETTER = function sessionStorageGet( key ){
- return JSON.parse( this.getItem( key ) );
+ var item = this.getItem( key );
+ return ( item !== null )?( JSON.parse( this.getItem( key ) ) ):( null );
},
STORAGE_ENGINE_SETTER = function sessionStorageSet( key, val ){
return this.setItem( key, JSON.stringify( val ) );
@@ -182,7 +182,7 @@
}
//??: more readable to make another class?
- var returnedStorage = {};
+ var returnedStorage = {},
// attempt to get starting data from engine...
data = STORAGE_ENGINE_GETTER.call( STORAGE_ENGINE, storageKey );
@@ -216,3 +216,63 @@
return returnedStorage;
};
+
+
+//==============================================================================
+function LoadingIndicator( $where ){
+ var self = this,
+ $indicator;
+
+ function setPosition(){
+ // even tho pos is 'fixed' - give illusion of width 100% and margin by manually setting width, offset
+ var padding = 4,
+ width = $indicator.parent().width() || $where.width(),
+ offset = $indicator.parent().offset() || $where.offset();
+
+ $indicator.outerWidth( width - ( padding * 2 ) );
+ // have to use css top, left and not offset (wont work when indicator is hidden)
+ $indicator.css({ top: offset.top + padding + 'px' , left: offset.left + padding + 'px' });
+ }
+
+ function render(){
+ var $spinner = $( '<span class="fa-icon-spinner fa-icon-spin fa-icon-large"></span>')
+ .css({ 'color' : 'grey', 'font-size' : '16px' });
+ var $message = $( '<i>loading...</i>' )
+ .css({ 'color' : 'grey', 'margin-left' : '8px' });
+ $indicator = $( '<div/>' ).addClass( 'loading-indicator' )
+ .css({
+ 'position' : 'fixed',
+ 'padding' : '4px',
+ 'text-align' : 'center',
+ 'background-color' : 'white',
+ 'opacity' : '0.85',
+ 'border-radius' : '3px'
+ })
+ .append( $spinner, $message )
+ //NOTE: insert as sibling to $where
+ .insertBefore( $where );
+ setPosition();
+ return $indicator.hide();
+ }
+
+ self.show = function( speed, callback ){
+ speed = speed || 'fast';
+ setPosition();
+ $indicator.fadeIn( speed, callback );
+ // not using full fadeOut allows using scroll to still work
+ //$whatIsLoading.fadeTo( speed, 0.0001, callback );
+ return self;
+ };
+
+ self.hide = function( speed, callback ){
+ speed = speed || 'fast';
+ //$whatIsLoading.fadeTo( speed, 1.0, function(){
+ // if( callback ){ callback(); }
+ //});
+ $indicator.fadeOut( speed, callback );
+ return self;
+ };
+ $indicator = render();
+ return self;
+}
+
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce static/scripts/mvc/dataset/hda-base.js
--- a/static/scripts/mvc/dataset/hda-base.js
+++ b/static/scripts/mvc/dataset/hda-base.js
@@ -1,7 +1,6 @@
-//define([
-// "../mvc/base-mvc"
-//], function(){
-
+define([
+ "mvc/dataset/hda-model"
+], function( hdaModel ){
/* global Backbone, LoggableMixin, HistoryDatasetAssociation, HDABaseView */
//==============================================================================
/** @class Read only view for HistoryDatasetAssociation.
@@ -22,6 +21,8 @@
tagName : "div",
className : "historyItemContainer",
+ fxSpeed : 'fast',
+
// ......................................................................... SET UP
/** Set up the view, cache url templates, bind listeners
* @param {Object} attributes
@@ -38,33 +39,20 @@
this._render_showParamsButton
];
- // cache urlTemplates (gen. provided by GalaxyPaths) to urls
- if( !attributes.urlTemplates ){ throw( 'HDAView needs urlTemplates on initialize' ); }
- this.urlTemplates = attributes.urlTemplates;
-
/** is the body of this hda view expanded/not. */
this.expanded = attributes.expanded || false;
+ this._setUpListeners();
+ },
+ _setUpListeners : function(){
// re-rendering on any model changes
- this.model.bind( 'change', function( model, options ){
- // if more than the display apps have changed: render everything
- var nonDisplayAppChanges = _.omit( this.model.changedAttributes(), 'display_apps', 'display_types' );
- if( _.keys( nonDisplayAppChanges ).length ){
- this.render();
+ this.model.on( 'change', this.render, this );
- // if just the display links, and it's already expanded: render the links only
- } else {
- if( this.expanded ){
- this._render_displayApps();
- }
- }
- }, this );
-
- //this.bind( 'all', function( event ){
+ //this.on( 'all', function( event ){
// this.log( event );
//}, this );
},
-
+
// ......................................................................... RENDER MAIN
/** Render this HDA, set up ui.
* @fires rendered:ready when rendered and NO running HDAs
@@ -86,9 +74,8 @@
// handle that here by removing previous view's tooltips
this.$el.find("[title]").tooltip( "destroy" );
- /** web controller urls for functions relating to this hda.
- * These are rendered from urlTemplates using the model data. */
- this.urls = this._renderUrls( this.urlTemplates, this.model.toJSON() );
+ /** web controller urls for functions relating to this hda. */
+ this.urls = this.model.urls();
itemWrapper
.addClass( 'historyItemWrapper' ).addClass( 'historyItem' )
@@ -104,9 +91,9 @@
itemWrapper.append( this.body );
// transition...
- this.$el.fadeOut( 'fast', function(){
+ this.$el.fadeOut( this.fxSpeed, function(){
view.$el.children().remove();
- view.$el.append( itemWrapper ).fadeIn( 'fast', function(){
+ view.$el.append( itemWrapper ).fadeIn( view.fxSpeed, function(){
view.log( view + ' rendered:', view.$el );
var renderedEventName = 'rendered';
@@ -121,55 +108,6 @@
return this;
},
- /** render the urls for this hda using the model data and the url templates from initialize.
- * @param {Object} urlTemplates a map (or nested map) of underscore templates (currently, anyhoo)
- * @param {Object} modelJson data from the model
- * @returns {Object} the templated urls
- */
- _renderUrls : function( urlTemplates, modelJson ){
- var hdaView = this,
- urls = {};
- _.each( urlTemplates, function( urlTemplateOrObj, urlKey ){
- // object == nested templates: recurse
- if( _.isObject( urlTemplateOrObj ) ){
- urls[ urlKey ] = hdaView._renderUrls( urlTemplateOrObj, modelJson );
-
- // string == template:
- } else {
- // meta_down load is a special case (see renderMetaDownloadUrls)
- //TODO: should be a better (gen.) way to handle this case
- if( urlKey === 'meta_download' ){
- urls[ urlKey ] = hdaView._renderMetaDownloadUrls( urlTemplateOrObj, modelJson );
-
- } else {
- try {
- urls[ urlKey ] = _.template( urlTemplateOrObj, modelJson );
- } catch( Error ){
- throw( hdaView + '._renderUrls error: ' + Error +
- '\n rendering:' + urlTemplateOrObj +
- '\n with ' + JSON.stringify( modelJson ) );
- }
- }
- }
- });
- return urls;
- },
-
- /** there can be more than one meta_file (e.g. bam index) to download,
- * so return a list of url and file_type for each
- * @param {Object} urlTemplate underscore templates for meta download urls
- * @param {Object} modelJson data from the model
- * @returns {Object} url and filetype for each meta file
- */
- _renderMetaDownloadUrls : function( urlTemplate, modelJson ){
- return _.map( modelJson.meta_files, function( meta_file ){
- return {
- url : _.template( urlTemplate, { id: modelJson.id, file_type: meta_file.file_type }),
- file_type : meta_file.file_type
- };
- });
- },
-
/** set up js behaviors, event handlers for elements within the given container
* @param {jQuery} $container jq object that contains the elements to process (defaults to this.$el)
*/
@@ -218,8 +156,8 @@
_render_displayButton : function(){
// don't show display if not viewable or not accessible
// (do show if in error, running)
- if( ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NEW )
+ if( ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NEW )
|| ( !this.model.get( 'accessible' ) ) ){
this.displayButton = null;
return null;
@@ -237,7 +175,7 @@
displayBtnData.title = _l( 'Cannot display datasets removed from disk' );
// disable if still uploading
- } else if( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.UPLOAD ){
+ } else if( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.UPLOAD ){
displayBtnData.enabled = false;
displayBtnData.title = _l( 'This dataset must finish uploading before it can be viewed' );
@@ -406,40 +344,40 @@
body.html( '' );
//TODO: not a fan of this dispatch
switch( this.model.get( 'state' ) ){
- case HistoryDatasetAssociation.STATES.NEW :
+ case hdaModel.HistoryDatasetAssociation.STATES.NEW :
this._render_body_new( body );
break;
- case HistoryDatasetAssociation.STATES.NOT_VIEWABLE :
+ case hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE :
this._render_body_not_viewable( body );
break;
- case HistoryDatasetAssociation.STATES.UPLOAD :
+ case hdaModel.HistoryDatasetAssociation.STATES.UPLOAD :
this._render_body_uploading( body );
break;
- case HistoryDatasetAssociation.STATES.PAUSED:
+ case hdaModel.HistoryDatasetAssociation.STATES.PAUSED:
this._render_body_paused( body );
break;
- case HistoryDatasetAssociation.STATES.QUEUED :
+ case hdaModel.HistoryDatasetAssociation.STATES.QUEUED :
this._render_body_queued( body );
break;
- case HistoryDatasetAssociation.STATES.RUNNING :
+ case hdaModel.HistoryDatasetAssociation.STATES.RUNNING :
this._render_body_running( body );
break;
- case HistoryDatasetAssociation.STATES.ERROR :
+ case hdaModel.HistoryDatasetAssociation.STATES.ERROR :
this._render_body_error( body );
break;
- case HistoryDatasetAssociation.STATES.DISCARDED :
+ case hdaModel.HistoryDatasetAssociation.STATES.DISCARDED :
this._render_body_discarded( body );
break;
- case HistoryDatasetAssociation.STATES.SETTING_METADATA :
+ case hdaModel.HistoryDatasetAssociation.STATES.SETTING_METADATA :
this._render_body_setting_metadata( body );
break;
- case HistoryDatasetAssociation.STATES.EMPTY :
+ case hdaModel.HistoryDatasetAssociation.STATES.EMPTY :
this._render_body_empty( body );
break;
- case HistoryDatasetAssociation.STATES.FAILED_METADATA :
+ case hdaModel.HistoryDatasetAssociation.STATES.FAILED_METADATA :
this._render_body_failed_metadata( body );
break;
- case HistoryDatasetAssociation.STATES.OK :
+ case hdaModel.HistoryDatasetAssociation.STATES.OK :
this._render_body_ok( body );
break;
default:
@@ -591,27 +529,44 @@
* @fires body-expanded when a body has been expanded
* @fires body-collapsed when a body has been collapsed
*/
- toggleBodyVisibility : function( event, expanded ){
+ toggleBodyVisibility : function( event, expand ){
var hdaView = this;
- this.expanded = ( expanded === undefined )?( !this.body.is( ':visible' ) ):( expanded );
- //this.log( 'toggleBodyVisibility, expanded:', expanded, '$body:', $body );
+ expand = ( expand === undefined )?( !this.body.is( ':visible' ) ):( expand );
+ if( expand ){
+ if( this.model.inReadyState() && !this.model.hasDetails() ){
+ var xhr = this.model.fetch();
+ xhr.done( function( model ){
+ hdaView.expandBody();
+ });
+ } else {
+ this.expandBody();
+ }
+ } else {
+ this.collapseBody();
+ }
+ },
- if( this.expanded ){
- hdaView._render_body_html( hdaView.body );
- this.body.slideDown( 'fast', function(){
- hdaView.trigger( 'body-expanded', hdaView.model.get( 'id' ) );
- });
- } else {
- this.body.slideUp( 'fast', function(){
- hdaView.trigger( 'body-collapsed', hdaView.model.get( 'id' ) );
- });
- }
+ expandBody : function(){
+ var hdaView = this;
+ hdaView._render_body_html( hdaView.body );
+ this.body.slideDown( hdaView.fxSpeed, function(){
+ hdaView.expanded = true;
+ hdaView.trigger( 'body-expanded', hdaView.model.get( 'id' ) );
+ });
+ },
+
+ collapseBody : function(){
+ var hdaView = this;
+ this.body.slideUp( hdaView.fxSpeed, function(){
+ hdaView.expanded = false;
+ hdaView.trigger( 'body-collapsed', hdaView.model.get( 'id' ) );
+ });
},
// ......................................................................... DELETION
remove : function( callback ){
var hdaView = this;
- this.$el.fadeOut( 'fast', function(){
+ this.$el.fadeOut( hdaView.fxSpeed, function(){
hdaView.$el.remove();
hdaView.off();
if( callback ){ callback(); }
@@ -638,6 +593,6 @@
};
//==============================================================================
-//return {
-// HDABaseView : HDABaseView,
-//};});
+return {
+ HDABaseView : HDABaseView,
+};});
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce static/scripts/mvc/dataset/hda-edit.js
--- a/static/scripts/mvc/dataset/hda-edit.js
+++ b/static/scripts/mvc/dataset/hda-edit.js
@@ -1,6 +1,7 @@
-//define([
-// "../mvc/base-mvc"
-//], function(){
+define([
+ "mvc/dataset/hda-model",
+ "mvc/dataset/hda-base"
+], function( hdaModel, hdaBase ){
//==============================================================================
/** @class Editing view for HistoryDatasetAssociation.
* @name HDAEditView
@@ -10,7 +11,7 @@
* @borrows LoggableMixin#log as #log
* @constructs
*/
-var HDAEditView = HDABaseView.extend( LoggableMixin ).extend(
+var HDAEditView = hdaBase.HDABaseView.extend( LoggableMixin ).extend(
/** @lends HDAEditView.prototype */{
// ......................................................................... SET UP
@@ -22,7 +23,8 @@
* @see HDABaseView#initialize
*/
initialize : function( attributes ){
- HDABaseView.prototype.initialize.call( this, attributes );
+ hdaBase.HDABaseView.prototype.initialize.call( this, attributes );
+ this.hasUser = attributes.hasUser;
/** list of rendering functions for the default, primary icon-buttons. */
this.defaultPrimaryActionButtonRenderers = [
@@ -37,33 +39,8 @@
* @param {jQuery} $container jq object that contains the elements to process (defaults to this.$el)
*/
_setUpBehaviors : function( $container ){
- //TODO: ideally this would be a DELETE call to the api
- // using purge async for now
- HDABaseView.prototype._setUpBehaviors.call( this, $container );
-
- // use purge_async with an ajax call
- var hdaView = this,
- purge_url = this.urls.purge,
- purge_link = $container.find( '#historyItemPurger-' + this.model.get( 'id' ) );
- if( purge_link ){
- //TODO: remove href from template
- purge_link.attr( 'href', [ "javascript", "void(0)" ].join( ':' ) );
- purge_link.click( function( event ){
- //TODO??: confirm?
- var xhr = jQuery.ajax( purge_url );
- xhr.success( function( message, status, responseObj ){
- hdaView.model.set( 'purged', true );
- hdaView.trigger( 'purged', hdaView );
- });
- xhr.error( function( error, status, message ){
- //TODO: Exception messages are hidden within error page
- //!NOTE: that includes the 'Removal of datasets by users is not allowed in this Galaxy instance.'
- view.trigger( 'error',
- hdaView, xhr, { url: purge_url }, _l( "Unable to purge this dataset" ) );
- });
- });
- }
- //TODO: same with undelete_async
+ hdaBase.HDABaseView.prototype._setUpBehaviors.call( this, $container );
+ //var hdaView = this;
},
// ......................................................................... RENDER WARNINGS
@@ -74,7 +51,7 @@
*/
_render_warnings : function(){
// jQ errs on building dom with whitespace - if there are no messages, trim -> ''
- return $( jQuery.trim( HDABaseView.templates.messages(
+ return $( jQuery.trim( hdaBase.HDABaseView.templates.messages(
_.extend( this.model.toJSON(), { urls: this.urls } )
)));
},
@@ -101,9 +78,9 @@
// don't show edit while uploading, in-accessible
// DO show if in error (ala previous history panel)
//TODO??: not viewable/accessible are essentially the same (not viewable set from accessible)
- if( ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NEW )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.UPLOAD )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
+ if( ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NEW )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.UPLOAD )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
|| ( !this.model.get( 'accessible' ) ) ){
this.editButton = null;
return null;
@@ -138,44 +115,26 @@
_render_deleteButton : function(){
// don't show delete if...
//TODO??: not viewable/accessible are essentially the same (not viewable set from accessible)
- if( ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NEW )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
+ if( ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NEW )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
|| ( !this.model.get( 'accessible' ) ) ){
this.deleteButton = null;
return null;
}
var self = this,
+ id = 'historyItemDeleter-' + self.model.get( 'id' ),
delete_url = self.urls[ 'delete' ],
deleteBtnData = {
- title : _l( 'Delete' ),
- href : delete_url,
- id : 'historyItemDeleter-' + this.model.get( 'id' ),
- icon_class : 'delete',
- on_click : function() {
- // Delete the dataset on the server and update HDA + view depending on success/failure.
- // FIXME: when HDA-delete is implemented in the API, can call set(), then save directly
- // on the model.
- $.ajax({
- url: delete_url,
- type: 'POST',
- error: function() {
- // Something went wrong, so show HDA again.
- // TODO: an error notification would be good.
- self.trigger( 'error', self, null, null, { url: delete_url }, _l( 'deletion failed' ) );
- self.$el.show();
- },
- success: function() {
- // FIXME: setting model attribute causes re-rendering, which is unnecessary.
- //self.$el.remove();
-
- self.model.set({ deleted: true });
- }
- });
-
- // Return false so that anchor action (page reload) does not happen.
- //return false;
- }
+ title : _l( 'Delete' ),
+ href : delete_url,
+ id : id,
+ icon_class : 'delete',
+ on_click : function() {
+ // ...bler... tooltips being left behind in DOM (hover out never called on deletion)
+ self.$el.find( '.menu-button.delete' ).trigger( 'mouseout' );
+ self.model[ 'delete' ]();
+ }
};
if( this.model.get( 'deleted' ) || this.model.get( 'purged' ) ){
deleteBtnData = {
@@ -202,7 +161,7 @@
//TODO: use HDABaseView and select/replace base on this switch
_.extend( modelData, { dbkey_unknown_and_editable : true });
}
- return HDABaseView.templates.hdaSummary( modelData );
+ return hdaBase.HDABaseView.templates.hdaSummary( modelData );
},
// ......................................................................... primary actions
@@ -210,7 +169,7 @@
* @returns {jQuery} rendered DOM
*/
_render_errButton : function(){
- if( this.model.get( 'state' ) !== HistoryDatasetAssociation.STATES.ERROR ){
+ if( this.model.get( 'state' ) !== hdaModel.HistoryDatasetAssociation.STATES.ERROR ){
this.errButton = null;
return null;
}
@@ -378,8 +337,7 @@
//TODO: these should be a sub-MV
_render_tagButton : function(){
//TODO: check for User
- if( !( this.model.hasData() )
- || ( !this.urls.tags.get ) ){
+ if( !this.hasUser || !this.urls.tags.get ){
this.tagButton = null;
return null;
}
@@ -399,8 +357,7 @@
//TODO: these should be a sub-MV
_render_annotateButton : function(){
//TODO: check for User
- if( !( this.model.hasData() )
- || ( !this.urls.annotation.get ) ){
+ if( !this.hasUser || !this.urls.annotation.get ){
this.annotateButton = null;
return null;
}
@@ -417,8 +374,8 @@
/** Render area to display tags.
* @returns {jQuery} rendered DOM
*/
- //TODO: into sub-MV
- //TODO: check for User
+//TODO: into sub-MV
+//TODO: check for User
_render_tagArea : function(){
if( !this.urls.tags.set ){ return null; }
//TODO: move to mvc/tags.js
@@ -430,8 +387,8 @@
/** Render area to display annotation.
* @returns {jQuery} rendered DOM
*/
- //TODO: into sub-MV
- //TODO: check for User
+//TODO: into sub-MV
+//TODO: check for User
_render_annotationArea : function(){
if( !this.urls.annotation.get ){ return null; }
//TODO: move to mvc/annotations.js
@@ -447,7 +404,7 @@
* @see HDABaseView#_render_body_error
*/
_render_body_error : function( parent ){
- HDABaseView.prototype._render_body_error.call( this, parent );
+ hdaBase.HDABaseView.prototype._render_body_error.call( this, parent );
var primaryActions = parent.find( '#primary-actions-' + this.model.get( 'id' ) );
primaryActions.prepend( this._render_errButton() );
},
@@ -498,11 +455,21 @@
/** event map */
events : {
'click .historyItemTitle' : 'toggleBodyVisibility',
+ 'click .historyItemUndelete' : function( ev ){ this.model.undelete(); return false; },
+ 'click .historyItemUnhide' : function( ev ){ this.model.unhide(); return false; },
+ 'click .historyItemPurge' : 'confirmPurge',
+
'click a.icon-button.tags' : 'loadAndDisplayTags',
'click a.icon-button.annotate' : 'loadAndDisplayAnnotation'
},
// ......................................................................... STATE CHANGES / MANIPULATION
+ confirmPurge : function _confirmPurge( ev ){
+ //TODO: confirm dialog
+ this.model.purge({ url: this.urls.purge });
+ return false;
+ },
+
/** Find the tag area and, if initial: load the html (via ajax) for displaying them; otherwise, unhide/hide
*/
//TODO: into sub-MV
@@ -523,30 +490,29 @@
url: this.urls.tags.get,
error: function( xhr, status, error ){
view.log( "Tagging failed", xhr, status, error );
- view.trigger( 'error', view, xhr, { url: view.urls.tags.get }, _l( "Tagging failed" ) );
+ view.trigger( 'error', view, xhr, {}, _l( "Tagging failed" ) );
},
success: function(tag_elt_html) {
tagElt.html(tag_elt_html);
tagElt.find("[title]").tooltip();
- tagArea.slideDown("fast");
+ tagArea.slideDown( view.fxSpeed );
}
});
} else {
// Tag element is filled; show.
- tagArea.slideDown("fast");
+ tagArea.slideDown( view.fxSpeed );
}
} else {
// Hide.
- tagArea.slideUp("fast");
+ tagArea.slideUp( view.fxSpeed );
}
return false;
},
/** Find the annotation area and, if initial: load the html (via ajax) for displaying them; otherwise, unhide/hide
*/
- //TODO: into sub-MV
loadAndDisplayAnnotation : function( event ){
- //TODO: this is a drop in from history.mako - should use MV as well
+//TODO: this is a drop in from history.mako - should use MV as well
this.log( this + '.loadAndDisplayAnnotation', event );
var view = this,
annotationArea = this.$el.find( '.annotation-area' ),
@@ -559,10 +525,9 @@
// Need to fill annotation element.
$.ajax({
url: this.urls.annotation.get,
- error: function( xhr, status, message ){
- view.log( "Annotation failed", xhr, status, message );
- view.trigger( 'error',
- view, xhr, { url: view.urls.annotation.get }, _l( "Annotation failed" ) );
+ error: function(){
+ view.log( "Annotation failed", xhr, status, error );
+ view.trigger( 'error', view, xhr, {}, _l( "Annotation failed" ) );
},
success: function( htmlFromAjax ){
if( htmlFromAjax === "" ){
@@ -576,16 +541,16 @@
setAnnotationUrl,
"new_annotation", 18, true, 4
);
- annotationArea.slideDown("fast");
+ annotationArea.slideDown( view.fxSpeed );
}
});
} else {
- annotationArea.slideDown("fast");
+ annotationArea.slideDown( view.fxSpeed );
}
} else {
// Hide.
- annotationArea.slideUp("fast");
+ annotationArea.slideUp( view.fxSpeed );
}
return false;
},
@@ -712,6 +677,6 @@
//==============================================================================
-//return {
-// HDAView : HDAView,
-//};});
+return {
+ HDAEditView : HDAEditView,
+};});
diff -r 902bf096a4aa1be446676d178ac5f6db4e5b558f -r bb8975aafcd91ca055ab5aa64a7b8e6a866f8cce static/scripts/mvc/dataset/hda-model.js
--- a/static/scripts/mvc/dataset/hda-model.js
+++ b/static/scripts/mvc/dataset/hda-model.js
@@ -1,6 +1,5 @@
-//define([
-// "../mvc/base-mvc"
-//], function(){
+define([
+], function(){
//==============================================================================
/** @class (HDA) model for a Galaxy dataset
* related to a history.
@@ -34,6 +33,13 @@
name : '(unnamed dataset)',
// one of HistoryDatasetAssociation.STATES
state : 'new',
+
+ deleted : false,
+ visible : true,
+
+ accessible : true,
+ purged : false,
+
// sniffed datatype (sam, tabular, bed, etc.)
data_type : null,
// size in bytes
@@ -44,37 +50,67 @@
meta_files : [],
misc_blurb : '',
- misc_info : '',
-
- deleted : false,
- purged : false,
- visible : true,
- accessible : true
+ misc_info : ''
},
/** fetch location of this history in the api */
urlRoot: 'api/histories/',
url : function(){
- //TODO: get this via url router
return this.urlRoot + this.get( 'history_id' ) + '/contents/' + this.get( 'id' );
- //TODO: this breaks on save()
},
+ urls : function(){
+ var id = this.get( 'id' );
+ if( !id ){ return {}; }
+ var urls = {
+ 'delete' : '/datasets/' + id + '/delete_async',
+ 'purge' : '/datasets/' + id + '/purge_async',
+ 'unhide' : '/datasets/' + id + '/unhide',
+ 'undelete' : '/datasets/' + id + '/undelete',
+
+ 'display' : '/datasets/' + id + '/display/?preview=True',
+ 'download' : '/datasets/' + id + '/display?to_ext=' + this.get( 'file_ext' ),
+ 'edit' : '/datasets/' + id + '/edit',
+ 'report_error': '/dataset/errors?id=' + id,
+ 'rerun' : '/tool_runner/rerun?id=' + id,
+ 'show_params': '/datasets/' + id + '/show_params',
+ 'visualization': '/visualization',
+
+ 'annotation': { 'get': '/dataset/get_annotation_async?id=' + id,
+ 'set': '/dataset/annotate_async?id=' + id },
+ 'tags' : { 'get': '/tag/get_tagging_elt_async?item_id=' + id + '&item_class=HistoryDatasetAssociation',
+ 'set': '/tag/retag?item_id=' + id + '&item_class=HistoryDatasetAssociation' }
+ };
+ //'meta_download': '/dataset/get_metadata_file?hda_id=%3C%25%3D+id+%25%3E&metadata_name=%3C%25%3D+file_type+%25%3E',
+ var meta_files = this.get( 'meta_files' );
+ if( meta_files ){
+ urls.meta_download = _.map( meta_files, function( meta_file ){
+ return {
+ //url : _.template( urlTemplate, { id: modelJson.id, file_type: meta_file.file_type }),
+ url : '/dataset/get_metadata_file?hda_id=' + id + '&metadata_name=' + meta_file.file_type,
+ file_type : meta_file.file_type
+ };
+ });
+ }
+ return urls;
+ },
+
/** Set up the model, determine if accessible, bind listeners
* @see Backbone.Model#initialize
*/
- //TODO:? use initialize (or validate) to check purged AND deleted -> purged XOR deleted
- initialize : function(){
+ initialize : function( data ){
this.log( this + '.initialize', this.attributes );
this.log( '\tparent history_id: ' + this.get( 'history_id' ) );
- // (curr) only handles changing state of non-accessible hdas to STATES.NOT_VIEWABLE
//!! this state is not in trans.app.model.Dataset.states - set it here -
- //TODO: change to server side.
if( !this.get( 'accessible' ) ){
this.set( 'state', HistoryDatasetAssociation.STATES.NOT_VIEWABLE );
}
+ this._setUpListeners();
+ },
+
+ _setUpListeners : function(){
// if the state has changed and the new state is a ready state, fire an event
this.on( 'change:state', function( currModel, newState ){
this.log( this + ' has changed state:', currModel, newState );
@@ -82,16 +118,9 @@
this.trigger( 'state:ready', currModel, newState, this.previous( 'state' ) );
}
});
-
- // debug on change events
- //this.on( 'change', function( currModel, changedList ){
- // this.log( this + ' has changed:', currModel, changedList );
- //});
- //this.bind( 'all', function( event ){
- // this.log( this + '', arguments );
- //});
},
+ // ........................................................................ common queries
/** Is this hda deleted or purged?
*/
isDeletedOrPurged : function(){
@@ -117,24 +146,21 @@
return isVisible;
},
+ hidden : function(){
+ return !this.get( 'visible' );
+ },
+
/** Is this HDA in a 'ready' state; where 'Ready' states are states where no
* processing (for the ds) is left to do on the server.
- * Currently: NEW, OK, EMPTY, FAILED_METADATA, NOT_VIEWABLE, DISCARDED,
- * and ERROR
*/
inReadyState : function(){
- var state = this.get( 'state' );
- //TODO: to list inclusion test
- //TODO: class level readyStates list
- return (
- this.isDeletedOrPurged()
- || ( state === HistoryDatasetAssociation.STATES.OK )
- || ( state === HistoryDatasetAssociation.STATES.EMPTY )
- || ( state === HistoryDatasetAssociation.STATES.FAILED_METADATA )
- || ( state === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
- || ( state === HistoryDatasetAssociation.STATES.DISCARDED )
- || ( state === HistoryDatasetAssociation.STATES.ERROR )
- );
+ var ready = _.contains( HistoryDatasetAssociation.READY_STATES, this.get( 'state' ) );
+ return ( this.isDeletedOrPurged() || ready );
+ },
+
+ hasDetails : function(){
+ //?? this may not be reliable
+ return _.has( this.attributes, 'genome_build' );
},
/** Convenience function to match hda.has_data.
@@ -144,6 +170,64 @@
return ( this.get( 'file_size' ) > 0 );
},
+ // ........................................................................ ajax
+ 'delete' : function _delete( options ){
+ return this.save( { deleted: true }, options );
+ },
+ undelete : function _undelete( options ){
+ return this.save( { deleted: false }, options );
+ },
+
+ hide : function _hide( options ){
+ return this.save( { visible: false }, options );
+ },
+ unhide : function _uhide( options ){
+ return this.save( { visible: true }, options );
+ },
+
+ purge : function _purge( options ){
+ //TODO: ideally this would be a DELETE call to the api
+ // using purge async for now
+ var hda = this,
+ xhr = jQuery.ajax( options );
+ xhr.done( function( message, status, responseObj ){
+ hda.set( 'purged', true );
+ });
+ xhr.fail( function( xhr, status, message ){
+ // Exception messages are hidden within error page including: '...not allowed in this Galaxy instance.'
+ // unbury and re-add to xhr
+ var error = _l( "Unable to purge this dataset" );
+ var messageBuriedInUnfortunatelyFormattedError = ( 'Removal of datasets by users '
+ + 'is not allowed in this Galaxy instance' );
+ if( xhr.responseJSON && xhr.responseJSON.error ){
+ error = xhr.responseJSON.error;
+ } else if( xhr.responseText.indexOf( messageBuriedInUnfortunatelyFormattedError ) !== -1 ){
+ error = messageBuriedInUnfortunatelyFormattedError;
+ }
+ xhr.responseText = error;
+ hda.trigger( 'error', hda, xhr, options, _l( error ), { error: error } );
+ });
+ },
+
+ // ........................................................................ sorting/filtering
+ searchKeys : [
+ 'name', 'file_ext', 'genome_build', 'misc_blurb', 'misc_info', 'annotation', 'tags'
+ ],
+
+ search : function( searchFor ){
+ var model = this;
+ searchFor = searchFor.toLowerCase();
+ return _.filter( this.searchKeys, function( key ){
+ var attr = model.get( key );
+ return ( _.isString( attr ) && attr.toLowerCase().indexOf( searchFor ) !== -1 );
+ });
+ },
+
+ matches : function( matchesWhat ){
+ return !!this.search( matchesWhat ).length;
+ },
+
+ // ........................................................................ misc
/** String representation
*/
toString : function(){
@@ -165,8 +249,6 @@
UPLOAD : 'upload',
/** the job that will produce the dataset queued in the runner */
QUEUED : 'queued',
- /** the job that will produce the dataset paused */
- PAUSED : 'paused',
/** the job that will produce the dataset is running */
RUNNING : 'running',
/** metadata for the dataset is being discovered/set */
@@ -180,6 +262,8 @@
/** has successfully completed running */
OK : 'ok',
+ /** the job that will produce the dataset paused */
+ PAUSED : 'paused',
/** metadata discovery/setting failed or errored (but otherwise ok) */
FAILED_METADATA : 'failed_metadata',
/** not accessible to the current user (i.e. due to permissions) */
@@ -190,6 +274,24 @@
ERROR : 'error'
};
+HistoryDatasetAssociation.READY_STATES = [
+ HistoryDatasetAssociation.STATES.NEW,
+ HistoryDatasetAssociation.STATES.OK,
+ HistoryDatasetAssociation.STATES.EMPTY,
+ HistoryDatasetAssociation.STATES.PAUSED,
+ HistoryDatasetAssociation.STATES.FAILED_METADATA,
+ HistoryDatasetAssociation.STATES.NOT_VIEWABLE,
+ HistoryDatasetAssociation.STATES.DISCARDED,
+ HistoryDatasetAssociation.STATES.ERROR
+];
+
+HistoryDatasetAssociation.NOT_READY_STATES = [
+ HistoryDatasetAssociation.STATES.UPLOAD,
+ HistoryDatasetAssociation.STATES.QUEUED,
+ HistoryDatasetAssociation.STATES.RUNNING,
+ HistoryDatasetAssociation.STATES.SETTING_METADATA
+];
+
//==============================================================================
/** @class Backbone collection of (HDA) models
*
@@ -204,83 +306,35 @@
///** logger used to record this.log messages, commonly set to console */
//// comment this out to suppress log output
//logger : console,
+ urlRoot : '/api/histories',
+ url : function(){
+ return this.urlRoot + '/' + this.historyId + '/contents';
+ },
/** Set up.
* @see Backbone.Collection#initialize
*/
- initialize : function(){
- //this.bind( 'all', function( event ){
- // this.log( this + '', arguments );
- //});
+ initialize : function( models, options ){
+ options = options || {};
+ this.historyId = options.historyId;
+ this._setUpListeners();
},
+ _setUpListeners : function(){
+ },
+
+ // ........................................................................ common queries
/** Get the ids of every hda in this collection
- * @returns array of encoded ids
+ * @returns array of encoded ids
*/
ids : function(){
return this.map( function( hda ){ return hda.id; });
},
- /** Get the hda with the given hid
- * @param {Int} hid the hid to search for
- * @returns {HistoryDatasetAssociation} the hda with the given hid or undefined if not found
- */
- getByHid : function( hid ){
- return _.first( this.filter( function( hda ){ return hda.get( 'hid' ) === hid; }) );
- },
-
- /** If the given hid is in the collection, return it's index. If not, return the insertion point it would need.
- * NOTE: assumes hids are unique and valid
- * @param {Int} hid the hid to find or create. If hid is 0, null, undefined: return the last hid + 1
- * @returns the collection index of the existing hda or an insertion point if it doesn't exist
- */
- hidToCollectionIndex : function( hid ){
- // if the hid is 0, null, undefined: assume a request for a new hid (return the last index)
- if( !hid ){
- return this.models.length;
- }
-
- var endingIndex = this.models.length - 1;
- //TODO: prob. more efficient to cycle backwards through these (assuming ordered by hid)
- for( var i=endingIndex; i>=0; i-- ){
- var hdaHid = this.at( i ).get( 'hid' );
- //this.log( i, 'hdaHid:', hdaHid );
- if( hdaHid === hid ){
- //this.log( '\t match:', hdaHid, hid, ' returning:', i );
- return i;
- }
- if( hdaHid < hid ){
- //this.log( '\t past it, returning:', ( i + 1 ) );
- return i + 1;
- }
- }
- return null;
- },
-
- /** Get every 'shown' hda in this collection based on show_deleted/hidden
- * @param {Boolean} show_deleted are we showing deleted hdas?
- * @param {Boolean} show_hidden are we showing hidden hdas?
- * @returns array of hda models
- * @see HistoryDatasetAssociation#isVisible
- */
- getVisible : function( show_deleted, show_hidden ){
- return this.filter( function( item ){ return item.isVisible( show_deleted, show_hidden ); });
- },
-
- /** For each possible hda state, get an array of all hda ids in that state
- * @returns a map of states -> hda ids
- * @see HistoryDatasetAssociation#STATES
- */
- getStateLists : function(){
- var stateLists = {};
- _.each( _.values( HistoryDatasetAssociation.STATES ), function( state ){
- stateLists[ state ] = [];
+ notReady : function(){
+ return this.filter( function( hda ){
+ return !hda.inReadyState();
});
- //NOTE: will err on unknown state
- this.each( function( item ){
- stateLists[ item.get( 'state' ) ].push( item.get( 'id' ) );
- });
- return stateLists;
},
/** Get the id of every hda in this collection not in a 'ready' state (running).
@@ -297,26 +351,55 @@
return idList;
},
- /** Update (fetch) the data of the hdas with the given ids.
- * @param {String[]} ids an array of hda ids to update
- * @returns {HistoryDatasetAssociation[]} hda models that were updated
- * @see HistoryDatasetAssociation#fetch
+ /** Get the hda with the given hid
+ * @param {Int} hid the hid to search for
+ * @returns {HistoryDatasetAssociation} the hda with the given hid or undefined if not found
*/
- update : function( ids ){
- this.log( this + 'update:', ids );
+ getByHid : function( hid ){
+ return _.first( this.filter( function( hda ){ return hda.get( 'hid' ) === hid; }) );
+ },
- if( !( ids && ids.length ) ){ return []; }
+ /** Get every 'shown' hda in this collection based on show_deleted/hidden
+ * @param {Boolean} show_deleted are we showing deleted hdas?
+ * @param {Boolean} show_hidden are we showing hidden hdas?
+ * @returns array of hda models
+ * @see HistoryDatasetAssociation#isVisible
+ */
+ getVisible : function( show_deleted, show_hidden ){
+ return this.filter( function( item ){ return item.isVisible( show_deleted, show_hidden ); });
+ },
- var collection = this,
- updatedHdas = null;
- _.each( ids, function( id, index ){
- var hda = collection.get( id );
- if( hda ){
- hda.fetch();
- updatedHdas.push( hda );
- }
+ // ........................................................................ ajax
+ fetchAllDetails : function(){
+ return this.fetch({ data : { details : 'all' } });
+ },
+
+ // ........................................................................ sorting/filtering
+ matches : function( matchesWhat ){
+ return this.filter( function( hda ){
+ return hda.matches( matchesWhat );
});
- return updatedHdas;
+ },
+
+ // ........................................................................ misc
+ set : function( models, options ){
+ // arrrrrrrrrrrrrrrrrg...
+ // override to get a correct/smarter merge when incoming data is partial (e.g. stupid backbone)
+ // w/o this partial models from the server will fill in missing data with model defaults
+ // and overwrite existing data on the client
+ // see Backbone.Collection.set and _prepareModel
+ var collection = this;
+ models = _.map( models, function( model ){
+ var existing = collection.get( model.id );
+ if( !existing ){ return model; }
+
+ // merge the models _BEFORE_ calling the superclass version
+ var merged = existing.toJSON();
+ _.extend( merged, model );
+ return merged;
+ });
+ // now call superclass when the data is filled
+ Backbone.Collection.prototype.set.call( this, models, options );
},
/** String representation. */
@@ -326,7 +409,7 @@
});
//==============================================================================
-//return {
-// HistoryDatasetAssociation : HistoryDatasetAssociation,
-// HDACollection : HDACollection,
-//};});
+return {
+ HistoryDatasetAssociation : HistoryDatasetAssociation,
+ HDACollection : HDACollection
+};});
This diff is so big that we needed to truncate the remainder.
https://bitbucket.org/galaxy/galaxy-central/commits/14fbaad2645b/
Changeset: 14fbaad2645b
Branch: next-stable
User: dannon
Date: 2013-10-21 23:32:34
Summary: Merge next-stable
Affected #: 3 files
diff -r 3b4cbba69871ab36384f1f8b28cb5555ba3dd20b -r 14fbaad2645bd7b8a0a2f9a4a682b38ecf18c7d0 lib/galaxy/web/__init__.py
--- a/lib/galaxy/web/__init__.py
+++ b/lib/galaxy/web/__init__.py
@@ -13,4 +13,5 @@
from framework import expose_api
from framework import expose_api_anonymous
from framework import expose_api_raw
+from framework import expose_api_raw_anonymous
from framework.base import httpexceptions
diff -r 3b4cbba69871ab36384f1f8b28cb5555ba3dd20b -r 14fbaad2645bd7b8a0a2f9a4a682b38ecf18c7d0 lib/galaxy/web/framework/__init__.py
--- a/lib/galaxy/web/framework/__init__.py
+++ b/lib/galaxy/web/framework/__init__.py
@@ -110,6 +110,14 @@
"""
return expose_api( func, to_json=False )
+#DBTODO refactor these post-dist.
+def expose_api_raw_anonymous( func ):
+ """
+ Expose this function via the API but don't dump the results
+ to JSON.
+ """
+ return expose_api( func, to_json=False, user_required=False )
+
def expose_api_anonymous( func, to_json=True ):
"""
Expose this function via the API but don't require a set user.
diff -r 3b4cbba69871ab36384f1f8b28cb5555ba3dd20b -r 14fbaad2645bd7b8a0a2f9a4a682b38ecf18c7d0 lib/galaxy/webapps/galaxy/api/datasets.py
--- a/lib/galaxy/webapps/galaxy/api/datasets.py
+++ b/lib/galaxy/webapps/galaxy/api/datasets.py
@@ -23,7 +23,7 @@
trans.response.status = 501
return 'not implemented'
- @web.expose_api
+ @web.expose_api_anonymous
def show( self, trans, id, hda_ldda='hda', data_type=None, provider=None, **kwd ):
"""
GET /api/datasets/{encoded_dataset_id}
@@ -101,7 +101,6 @@
# If there is a chrom, check for data on the chrom.
if chrom:
- data_provider_registry = trans.app.data_provider_registry
data_provider = trans.app.data_provider_registry.get_data_provider( trans,
original_dataset=dataset, source='index' )
if not data_provider.has_data( chrom ):
@@ -244,7 +243,7 @@
return data
- @web.expose_api_raw
+ @web.expose_api_raw_anonymous
def display( self, trans, history_content_id, history_id,
preview=False, filename=None, to_ext=None, chunk=None, **kwd ):
"""
https://bitbucket.org/galaxy/galaxy-central/commits/361f581d1e51/
Changeset: 361f581d1e51
User: dannon
Date: 2013-10-21 23:33:47
Summary: Merge
Affected #: 0 files
https://bitbucket.org/galaxy/galaxy-central/commits/315018626d87/
Changeset: 315018626d87
User: dannon
Date: 2013-10-21 23:34:09
Summary: Merge.
Affected #: 1 file
diff -r 361f581d1e5188b01476f6da5ca22af7d5c6ba5e -r 315018626d873654e822ef97984c0f3288360fb2 lib/galaxy/webapps/galaxy/api/histories.py
--- a/lib/galaxy/webapps/galaxy/api/histories.py
+++ b/lib/galaxy/webapps/galaxy/api/histories.py
@@ -113,7 +113,7 @@
except Exception, e:
msg = "Error in history API at showing history detail: %s" % ( str( e ) )
- log.exception( e )
+ log.exception( msg )
trans.response.status = 500
return msg
@@ -148,7 +148,7 @@
except Exception, e:
msg = "Error in history API when switching current history: %s" % ( str( e ) )
- log.exception( e )
+ log.exception( msg )
trans.response.status = 500
return msg
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.
1
0
commit/galaxy-central: carlfeberhard: Histories API: use proper logging technique for exceptions
by commits-noreply@bitbucket.org 21 Oct '13
by commits-noreply@bitbucket.org 21 Oct '13
21 Oct '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/80db2712720c/
Changeset: 80db2712720c
User: carlfeberhard
Date: 2013-10-21 23:32:12
Summary: Histories API: use proper logging technique for exceptions
Affected #: 1 file
diff -r fbf1898d7dea43a46a0f8ec80fd41540ac6fc204 -r 80db2712720c4ea153e51bbc72e981cc9886e73c lib/galaxy/webapps/galaxy/api/histories.py
--- a/lib/galaxy/webapps/galaxy/api/histories.py
+++ b/lib/galaxy/webapps/galaxy/api/histories.py
@@ -113,7 +113,7 @@
except Exception, e:
msg = "Error in history API at showing history detail: %s" % ( str( e ) )
- log.exception( e )
+ log.exception( msg )
trans.response.status = 500
return msg
@@ -148,7 +148,7 @@
except Exception, e:
msg = "Error in history API when switching current history: %s" % ( str( e ) )
- log.exception( e )
+ log.exception( msg )
trans.response.status = 500
return msg
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.
1
0
2 new commits in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/3b4cbba69871/
Changeset: 3b4cbba69871
Branch: next-stable
User: jgoecks
Date: 2013-10-21 23:11:17
Summary: Use progressive approach to integrate tabular chunked data display into collaboration framework. This fixes a bug that prevented chunkable datasets from being viewable in pages.
Affected #: 1 file
diff -r 81880a04e6e79d944a6d9c225b36417114cd38ec -r 3b4cbba69871ab36384f1f8b28cb5555ba3dd20b templates/webapps/galaxy/dataset/display.mako
--- a/templates/webapps/galaxy/dataset/display.mako
+++ b/templates/webapps/galaxy/dataset/display.mako
@@ -18,6 +18,12 @@
});
require(['mvc/data'], function(data) {
+ //
+ // Use tabular data display progressively by deleting data from page body
+ // and then showing dataset view.
+ //
+ $('.page-body').children().remove();
+
data.createTabularDatasetChunkedView(
// Dataset config. TODO: encode id.
_.extend( ${h.to_json_string( item.to_dict() )},
@@ -59,10 +65,10 @@
title="Import dataset"></a></%def>
+## Renders dataset content. Function is used to render data in stand-along page and to provide content for embedded datasets as well.
<%def name="render_item( data, data_to_render )">
- ## Chunkable data is rendered in JavaScript above; render unchunkable data below.
${ render_deleted_data_message( data ) }
- %if not data.datatype.CHUNKABLE and data_to_render:
+ %if data_to_render:
%if truncated:
<div class="warningmessagelarge">
This dataset is large and only the first megabyte is shown below. |
https://bitbucket.org/galaxy/galaxy-central/commits/fbf1898d7dea/
Changeset: fbf1898d7dea
User: jgoecks
Date: 2013-10-21 23:11:48
Summary: Automated merge of next-stable branch into default
Affected #: 1 file
diff -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a -r fbf1898d7dea43a46a0f8ec80fd41540ac6fc204 templates/webapps/galaxy/dataset/display.mako
--- a/templates/webapps/galaxy/dataset/display.mako
+++ b/templates/webapps/galaxy/dataset/display.mako
@@ -18,6 +18,12 @@
});
require(['mvc/data'], function(data) {
+ //
+ // Use tabular data display progressively by deleting data from page body
+ // and then showing dataset view.
+ //
+ $('.page-body').children().remove();
+
data.createTabularDatasetChunkedView(
// Dataset config. TODO: encode id.
_.extend( ${h.to_json_string( item.to_dict() )},
@@ -59,10 +65,10 @@
title="Import dataset"></a></%def>
+## Renders dataset content. Function is used to render data in stand-along page and to provide content for embedded datasets as well.
<%def name="render_item( data, data_to_render )">
- ## Chunkable data is rendered in JavaScript above; render unchunkable data below.
${ render_deleted_data_message( data ) }
- %if not data.datatype.CHUNKABLE and data_to_render:
+ %if data_to_render:
%if truncated:
<div class="warningmessagelarge">
This dataset is large and only the first megabyte is shown below. |
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.
1
0
commit/galaxy-central: carlfeberhard: History panel: remove from iframe, general improvements; pack scripts
by commits-noreply@bitbucket.org 21 Oct '13
by commits-noreply@bitbucket.org 21 Oct '13
21 Oct '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/4f1c25230dd0/
Changeset: 4f1c25230dd0
User: carlfeberhard
Date: 2013-10-21 22:26:47
Summary: History panel: remove from iframe, general improvements; pack scripts
Affected #: 28 files
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a lib/galaxy/web/base/controller.py
--- a/lib/galaxy/web/base/controller.py
+++ b/lib/galaxy/web/base/controller.py
@@ -633,11 +633,11 @@
# if a tool declares 'force_history_refresh' in its xml, when the hda -> ready, reload the history panel
# expensive
- if( ( hda.state in [ 'running', 'queued' ] )
- and ( hda.creating_job and hda.creating_job.tool_id ) ):
- tool_used = trans.app.toolbox.get_tool( hda.creating_job.tool_id )
- if tool_used and tool_used.force_history_refresh:
- hda_dict[ 'force_history_refresh' ] = True
+ #if( ( hda.state in [ 'running', 'queued' ] )
+ #and ( hda.creating_job and hda.creating_job.tool_id ) ):
+ # tool_used = trans.app.toolbox.get_tool( hda.creating_job.tool_id )
+ # if tool_used and tool_used.force_history_refresh:
+ # hda_dict[ 'force_history_refresh' ] = True
return trans.security.encode_dict_ids( hda_dict )
@@ -653,13 +653,14 @@
'accessible': False
})
- def get_hda_dict_with_error( self, trans, hda, error_msg='' ):
+ def get_hda_dict_with_error( self, trans, hda=None, history_id=None, id=None, error_msg='Error' ):
return trans.security.encode_dict_ids({
- 'id' : hda.id,
- 'history_id': hda.history.id,
- 'hid' : hda.hid,
- 'name' : hda.name,
- 'error' : error_msg
+ 'id' : hda.id if hda else id,
+ 'history_id': hda.history.id if hda else history_id,
+ 'hid' : hda.hid if hda else '(unknown)',
+ 'name' : hda.name if hda else '(unknown)',
+ 'error' : error_msg,
+ 'state' : trans.model.Dataset.states.NEW
})
def get_display_apps( self, trans, hda ):
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a lib/galaxy/webapps/galaxy/api/histories.py
--- a/lib/galaxy/webapps/galaxy/api/histories.py
+++ b/lib/galaxy/webapps/galaxy/api/histories.py
@@ -97,6 +97,9 @@
# Most recent active history for user sessions, not deleted
history = trans.user.galaxy_sessions[0].histories[-1].history
+ elif history_id == "current":
+ history = trans.get_history( create=True )
+
else:
history = self.get_history( trans, history_id, check_ownership=False,
check_accessible=True, deleted=deleted )
@@ -110,7 +113,7 @@
except Exception, e:
msg = "Error in history API at showing history detail: %s" % ( str( e ) )
- log.exception( msg, exc_info=True )
+ log.exception( e )
trans.response.status = 500
return msg
@@ -174,7 +177,8 @@
trans.sa_session.add( new_history )
trans.sa_session.flush()
- item = new_history.to_dict(view='element', value_mapper={'id':trans.security.encode_id})
+ #item = new_history.to_dict(view='element', value_mapper={'id':trans.security.encode_id})
+ item = self.get_history_dict( trans, new_history )
item['url'] = url_for( 'history', id=item['id'] )
#TODO: possibly default to True here - but favor explicit for now (and backwards compat)
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a lib/galaxy/webapps/galaxy/api/history_contents.py
--- a/lib/galaxy/webapps/galaxy/api/history_contents.py
+++ b/lib/galaxy/webapps/galaxy/api/history_contents.py
@@ -59,22 +59,21 @@
encoded_hda_id = trans.security.encode_id( hda.id )
if encoded_hda_id in ids:
#TODO: share code with show
- try:
- hda_dict = self.get_hda_dict( trans, hda )
- hda_dict[ 'display_types' ] = self.get_old_display_applications( trans, hda )
- hda_dict[ 'display_apps' ] = self.get_display_apps( trans, hda )
- rval.append( hda_dict )
-
- except Exception, exc:
- # don't fail entire list if hda err's, record and move on
- log.error( "Error in history API at listing contents with history %s, hda %s: (%s) %s",
- history_id, encoded_hda_id, type( exc ), str( exc ), exc_info=True )
- rval.append( self.get_hda_dict_with_error( trans, hda, str( exc ) ) )
+ rval.append( self._detailed_hda_dict( trans, hda ) )
# if no ids passed, return a _SUMMARY_ of _all_ datasets in the history
else:
+ details = kwd.get( 'details', None ) or []
+ if details and details != 'all':
+ details = util.listify( details )
+
for hda in history.datasets:
- rval.append( self._summary_hda_dict( trans, history_id, hda ) )
+ encoded_hda_id = trans.security.encode_id( hda.id )
+ if( ( encoded_hda_id in details )
+ or ( details == 'all' ) ):
+ rval.append( self._detailed_hda_dict( trans, hda ) )
+ else:
+ rval.append( self._summary_hda_dict( trans, history_id, hda ) )
except Exception, e:
# for errors that are not specific to one hda (history lookup or summary list)
@@ -85,7 +84,7 @@
return rval
#TODO: move to model or Mixin
- def _summary_hda_dict( self, trans, history_id, hda ):
+ def _summary_hda_dict( self, trans, encoded_history_id, hda ):
"""
Returns a dictionary based on the HDA in summary form::
{
@@ -99,11 +98,32 @@
encoded_id = trans.security.encode_id( hda.id )
return {
'id' : encoded_id,
+ 'history_id' : encoded_history_id,
'name' : hda.name,
'type' : api_type,
- 'url' : url_for( 'history_content', history_id=history_id, id=encoded_id, ),
+ 'state' : hda.state,
+ 'deleted': hda.deleted,
+ 'visible': hda.visible,
+ 'hid' : hda.hid,
+ 'url' : url_for( 'history_content', history_id=encoded_history_id, id=encoded_id, ),
}
+ def _detailed_hda_dict( self, trans, hda ):
+ """
+ Detailed dictionary of hda values.
+ """
+ try:
+ hda_dict = self.get_hda_dict( trans, hda )
+ hda_dict[ 'display_types' ] = self.get_old_display_applications( trans, hda )
+ hda_dict[ 'display_apps' ] = self.get_display_apps( trans, hda )
+ return hda_dict
+
+ except Exception, exc:
+ # catch error here - returning a briefer hda_dict with an error attribute
+ log.exception( "Error in history API at listing contents with history %s, hda %s: (%s) %s",
+ hda.history_id, hda.id, type( exc ), str( exc ) )
+ return self.get_hda_dict_with_error( trans, hda=hda, error_msg=str( exc ) )
+
@web.expose_api_anonymous
def show( self, trans, id, history_id, **kwd ):
"""
@@ -244,7 +264,7 @@
trans.response.status = 501
return
- @web.expose_api
+ @web.expose_api_anonymous
def update( self, trans, history_id, id, payload, **kwd ):
"""
update( self, trans, history_id, id, payload, **kwd )
@@ -269,10 +289,28 @@
#TODO: PUT /api/histories/{encoded_history_id} payload = { rating: rating } (w/ no security checks)
changed = {}
try:
- hda = self.get_dataset( trans, id,
- check_ownership=True, check_accessible=True, check_state=True )
- # validation handled here and some parsing, processing, and conversion
- payload = self._validate_and_parse_update_payload( payload )
+ # anon user
+ if trans.user == None:
+ if history_id != trans.security.encode_id( trans.history.id ):
+ trans.response.status = 401
+ return { 'error': 'Anonymous users cannot edit histories other than their current history' }
+
+ anon_allowed_payload = {}
+ if 'deleted' in payload:
+ anon_allowed_payload[ 'deleted' ] = payload[ 'deleted' ]
+ if 'visible' in payload:
+ anon_allowed_payload[ 'visible' ] = payload[ 'visible' ]
+
+ payload = self._validate_and_parse_update_payload( anon_allowed_payload )
+ hda = self.get_dataset( trans, id, check_ownership=False, check_accessible=False, check_state=True )
+ if hda.history != trans.history:
+ trans.response.status = 401
+ return { 'error': 'Anonymous users cannot edit datasets outside their current history' }
+
+ else:
+ payload = self._validate_and_parse_update_payload( payload )
+ hda = self.get_dataset( trans, id, check_ownership=True, check_accessible=True, check_state=True )
+
# additional checks here (security, etc.)
changed = self.set_hda_from_dict( trans, hda, payload )
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a lib/galaxy/webapps/galaxy/controllers/root.py
--- a/lib/galaxy/webapps/galaxy/controllers/root.py
+++ b/lib/galaxy/webapps/galaxy/controllers/root.py
@@ -5,7 +5,7 @@
import os
import urllib
-from paste.httpexceptions import HTTPNotFound
+from paste.httpexceptions import HTTPNotFound, HTTPBadGateway
from galaxy import web
from galaxy.web import url_for
@@ -30,7 +30,8 @@
@web.expose
def index(self, trans, id=None, tool_id=None, mode=None, workflow_id=None, m_c=None, m_a=None, **kwd):
- """Called on the root url to display the main Galaxy page.
+ """
+ Called on the root url to display the main Galaxy page.
"""
return trans.fill_template( "root/index.mako",
tool_id=tool_id,
@@ -99,63 +100,75 @@
show_deleted=string_as_bool( show_deleted ),
show_hidden=string_as_bool( show_hidden ) )
- @web.expose
- def history( self, trans, as_xml=False, show_deleted=None, show_hidden=None, hda_id=None, **kwd ):
- """Display the current history, creating a new history if necessary.
-
- NOTE: No longer accepts "id" or "template" options for security reasons.
- """
- if as_xml:
- return self.history_as_xml( trans,
- show_deleted=string_as_bool( show_deleted ), show_hidden=string_as_bool( show_hidden ) )
-
- # get all datasets server-side, client-side will get flags and render appropriately
- show_deleted = string_as_bool_or_none( show_deleted )
- show_purged = show_deleted
- show_hidden = string_as_bool_or_none( show_hidden )
- params = Params( kwd )
- message = params.get( 'message', '' )
- #TODO: ugh...
- message = message if message != 'None' else ''
- status = params.get( 'status', 'done' )
-
- if trans.app.config.require_login and not trans.user:
- return trans.fill_template( '/no_access.mako', message = 'Please log in to access Galaxy histories.' )
-
- def err_msg( where=None ):
- where = where if where else 'getting the history data from the server'
- err_msg = ( 'An error occurred %s. '
- + 'Please contact a Galaxy administrator if the problem persists.' ) %( where )
- return err_msg, 'error'
-
+ def _get_current_history_data( self, trans ):
history_dictionary = {}
hda_dictionaries = []
+
try:
history = trans.get_history( create=True )
hdas = self.get_history_datasets( trans, history,
show_deleted=True, show_hidden=True, show_purged=True )
for hda in hdas:
+ hda_dict = {}
try:
- hda_dictionaries.append( self.get_hda_dict( trans, hda ) )
+ hda_dict = self.get_hda_dict( trans, hda )
except Exception, exc:
# don't fail entire list if hda err's, record and move on
log.error( 'Error bootstrapping hda %d: %s', hda.id, str( exc ), exc_info=True )
- hda_dictionaries.append( self.get_hda_dict_with_error( trans, hda, str( exc ) ) )
+ hda_dict = self.get_hda_dict_with_error( trans, hda, str( exc ) )
+
+ hda_dictionaries.append( hda_dict )
# re-use the hdas above to get the history data...
history_dictionary = self.get_history_dict( trans, history, hda_dictionaries=hda_dictionaries )
except Exception, exc:
user_id = str( trans.user.id ) if trans.user else '(anonymous)'
- log.error( 'Error bootstrapping history for user %s: %s', user_id, str( exc ), exc_info=True )
- message, status = err_msg()
+ log.exception( 'Error bootstrapping history for user %s: %s', user_id, str( exc ) )
+ message = ( 'An error occurred getting the history data from the server. '
+ + 'Please contact a Galaxy administrator if the problem persists.' )
history_dictionary[ 'error' ] = message
- return trans.stream_template_mako( "root/history.mako",
- history_json = to_json_string( history_dictionary ), hda_json = to_json_string( hda_dictionaries ),
- show_deleted=show_deleted, show_hidden=show_hidden, hda_id=hda_id, log=log, message=message, status=status )
+ return {
+ 'history' : history_dictionary,
+ 'hdas' : hda_dictionaries
+ }
+
+ @web.expose
+ def history( self, trans, as_xml=False, show_deleted=None, show_hidden=None, **kwd ):
+ """
+ Display the current history in it's own page or as xml.
+ """
+ if as_xml:
+ return self.history_as_xml( trans,
+ show_deleted=string_as_bool( show_deleted ), show_hidden=string_as_bool( show_hidden ) )
+
+ if trans.app.config.require_login and not trans.user:
+ return trans.fill_template( '/no_access.mako', message = 'Please log in to access Galaxy histories.' )
+
+ # get all datasets server-side, client-side will get flags and render appropriately
+ show_deleted = string_as_bool_or_none( show_deleted )
+ show_purged = show_deleted
+ show_hidden = string_as_bool_or_none( show_hidden )
+
+ history_dictionary = {}
+ hda_dictionaries = []
+ try:
+ history_data = self._get_current_history_data( trans )
+ history_dictionary = history_data[ 'history' ]
+ hda_dictionaries = history_data[ 'hdas' ]
+
+ except Exception, exc:
+ user_id = str( trans.user.id ) if trans.user else '(anonymous)'
+ log.exception( 'Error bootstrapping history for user %s: %s', user_id, str( exc ) )
+ history_dictionary[ 'error' ] = ( 'An error occurred getting the history data from the server. '
+ + 'Please contact a Galaxy administrator if the problem persists.' )
+
+ return trans.fill_template_mako( "root/history.mako",
+ history = history_dictionary, hdas = hda_dictionaries,
+ show_deleted=show_deleted, show_hidden=show_hidden )
## ---- Dataset display / editing ----------------------------------------
@web.expose
@@ -503,7 +516,22 @@
return rval
@web.expose
- def generate_error( self, trans ):
+ def generate_error( self, trans, code=500 ):
"""Raises an exception (debugging).
"""
+ trans.response.status = code
raise Exception( "Fake error!" )
+
+ @web.json
+ def generate_json_error( self, trans, code=500 ):
+ """Raises an exception (debugging).
+ """
+ try:
+ code = int( code )
+ except Exception, exc:
+ code = 500
+
+ if code == 502:
+ raise HTTPBadGateway()
+ trans.response.status = code
+ return { 'error': 'Fake error!' }
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a lib/galaxy/webapps/galaxy/controllers/tool_runner.py
--- a/lib/galaxy/webapps/galaxy/controllers/tool_runner.py
+++ b/lib/galaxy/webapps/galaxy/controllers/tool_runner.py
@@ -325,4 +325,5 @@
<p><b>Please do not use your browser\'s "stop" or "reload" buttons until the upload is complete, or it may be interrupted.</b></p><p>You may safely continue to use Galaxy while the upload is in progress. Using "stop" and "reload" on pages other than Galaxy is also safe.</p>
"""
+ #return trans.show_message( msg, refresh_frames=[ 'history' ] )
return trans.show_message( msg )
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a static/scripts/mvc/base-mvc.js
--- a/static/scripts/mvc/base-mvc.js
+++ b/static/scripts/mvc/base-mvc.js
@@ -7,31 +7,30 @@
name: null,
hidden: false
},
-
+
show: function() {
this.set("hidden", false);
},
-
+
hide: function() {
this.set("hidden", true);
},
-
+
is_visible: function() {
return !this.attributes.hidden;
}
});
-
/**
* Base view that handles visibility based on model's hidden attribute.
*/
var BaseView = Backbone.View.extend({
-
+
initialize: function() {
this.model.on("change:hidden", this.update_visible, this);
this.update_visible();
},
-
+
update_visible: function() {
if( this.model.attributes.hidden ){
this.$el.hide();
@@ -120,7 +119,8 @@
// ~constants for the current engine
var STORAGE_ENGINE = sessionStorage,
STORAGE_ENGINE_GETTER = function sessionStorageGet( key ){
- return JSON.parse( this.getItem( key ) );
+ var item = this.getItem( key );
+ return ( item !== null )?( JSON.parse( this.getItem( key ) ) ):( null );
},
STORAGE_ENGINE_SETTER = function sessionStorageSet( key, val ){
return this.setItem( key, JSON.stringify( val ) );
@@ -182,7 +182,7 @@
}
//??: more readable to make another class?
- var returnedStorage = {};
+ var returnedStorage = {},
// attempt to get starting data from engine...
data = STORAGE_ENGINE_GETTER.call( STORAGE_ENGINE, storageKey );
@@ -216,3 +216,63 @@
return returnedStorage;
};
+
+
+//==============================================================================
+function LoadingIndicator( $where ){
+ var self = this,
+ $indicator;
+
+ function setPosition(){
+ // even tho pos is 'fixed' - give illusion of width 100% and margin by manually setting width, offset
+ var padding = 4,
+ width = $indicator.parent().width() || $where.width(),
+ offset = $indicator.parent().offset() || $where.offset();
+
+ $indicator.outerWidth( width - ( padding * 2 ) );
+ // have to use css top, left and not offset (wont work when indicator is hidden)
+ $indicator.css({ top: offset.top + padding + 'px' , left: offset.left + padding + 'px' });
+ }
+
+ function render(){
+ var $spinner = $( '<span class="fa-icon-spinner fa-icon-spin fa-icon-large"></span>')
+ .css({ 'color' : 'grey', 'font-size' : '16px' });
+ var $message = $( '<i>loading...</i>' )
+ .css({ 'color' : 'grey', 'margin-left' : '8px' });
+ $indicator = $( '<div/>' ).addClass( 'loading-indicator' )
+ .css({
+ 'position' : 'fixed',
+ 'padding' : '4px',
+ 'text-align' : 'center',
+ 'background-color' : 'white',
+ 'opacity' : '0.85',
+ 'border-radius' : '3px'
+ })
+ .append( $spinner, $message )
+ //NOTE: insert as sibling to $where
+ .insertBefore( $where );
+ setPosition();
+ return $indicator.hide();
+ }
+
+ self.show = function( speed, callback ){
+ speed = speed || 'fast';
+ setPosition();
+ $indicator.fadeIn( speed, callback );
+ // not using full fadeOut allows using scroll to still work
+ //$whatIsLoading.fadeTo( speed, 0.0001, callback );
+ return self;
+ };
+
+ self.hide = function( speed, callback ){
+ speed = speed || 'fast';
+ //$whatIsLoading.fadeTo( speed, 1.0, function(){
+ // if( callback ){ callback(); }
+ //});
+ $indicator.fadeOut( speed, callback );
+ return self;
+ };
+ $indicator = render();
+ return self;
+}
+
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a static/scripts/mvc/dataset/hda-base.js
--- a/static/scripts/mvc/dataset/hda-base.js
+++ b/static/scripts/mvc/dataset/hda-base.js
@@ -1,7 +1,6 @@
-//define([
-// "../mvc/base-mvc"
-//], function(){
-
+define([
+ "mvc/dataset/hda-model"
+], function( hdaModel ){
/* global Backbone, LoggableMixin, HistoryDatasetAssociation, HDABaseView */
//==============================================================================
/** @class Read only view for HistoryDatasetAssociation.
@@ -22,6 +21,8 @@
tagName : "div",
className : "historyItemContainer",
+ fxSpeed : 'fast',
+
// ......................................................................... SET UP
/** Set up the view, cache url templates, bind listeners
* @param {Object} attributes
@@ -38,33 +39,20 @@
this._render_showParamsButton
];
- // cache urlTemplates (gen. provided by GalaxyPaths) to urls
- if( !attributes.urlTemplates ){ throw( 'HDAView needs urlTemplates on initialize' ); }
- this.urlTemplates = attributes.urlTemplates;
-
/** is the body of this hda view expanded/not. */
this.expanded = attributes.expanded || false;
+ this._setUpListeners();
+ },
+ _setUpListeners : function(){
// re-rendering on any model changes
- this.model.bind( 'change', function( model, options ){
- // if more than the display apps have changed: render everything
- var nonDisplayAppChanges = _.omit( this.model.changedAttributes(), 'display_apps', 'display_types' );
- if( _.keys( nonDisplayAppChanges ).length ){
- this.render();
+ this.model.on( 'change', this.render, this );
- // if just the display links, and it's already expanded: render the links only
- } else {
- if( this.expanded ){
- this._render_displayApps();
- }
- }
- }, this );
-
- //this.bind( 'all', function( event ){
+ //this.on( 'all', function( event ){
// this.log( event );
//}, this );
},
-
+
// ......................................................................... RENDER MAIN
/** Render this HDA, set up ui.
* @fires rendered:ready when rendered and NO running HDAs
@@ -86,9 +74,8 @@
// handle that here by removing previous view's tooltips
this.$el.find("[title]").tooltip( "destroy" );
- /** web controller urls for functions relating to this hda.
- * These are rendered from urlTemplates using the model data. */
- this.urls = this._renderUrls( this.urlTemplates, this.model.toJSON() );
+ /** web controller urls for functions relating to this hda. */
+ this.urls = this.model.urls();
itemWrapper
.addClass( 'historyItemWrapper' ).addClass( 'historyItem' )
@@ -104,9 +91,9 @@
itemWrapper.append( this.body );
// transition...
- this.$el.fadeOut( 'fast', function(){
+ this.$el.fadeOut( this.fxSpeed, function(){
view.$el.children().remove();
- view.$el.append( itemWrapper ).fadeIn( 'fast', function(){
+ view.$el.append( itemWrapper ).fadeIn( view.fxSpeed, function(){
view.log( view + ' rendered:', view.$el );
var renderedEventName = 'rendered';
@@ -121,55 +108,6 @@
return this;
},
- /** render the urls for this hda using the model data and the url templates from initialize.
- * @param {Object} urlTemplates a map (or nested map) of underscore templates (currently, anyhoo)
- * @param {Object} modelJson data from the model
- * @returns {Object} the templated urls
- */
- _renderUrls : function( urlTemplates, modelJson ){
- var hdaView = this,
- urls = {};
- _.each( urlTemplates, function( urlTemplateOrObj, urlKey ){
- // object == nested templates: recurse
- if( _.isObject( urlTemplateOrObj ) ){
- urls[ urlKey ] = hdaView._renderUrls( urlTemplateOrObj, modelJson );
-
- // string == template:
- } else {
- // meta_down load is a special case (see renderMetaDownloadUrls)
- //TODO: should be a better (gen.) way to handle this case
- if( urlKey === 'meta_download' ){
- urls[ urlKey ] = hdaView._renderMetaDownloadUrls( urlTemplateOrObj, modelJson );
-
- } else {
- try {
- urls[ urlKey ] = _.template( urlTemplateOrObj, modelJson );
- } catch( Error ){
- throw( hdaView + '._renderUrls error: ' + Error +
- '\n rendering:' + urlTemplateOrObj +
- '\n with ' + JSON.stringify( modelJson ) );
- }
- }
- }
- });
- return urls;
- },
-
- /** there can be more than one meta_file (e.g. bam index) to download,
- * so return a list of url and file_type for each
- * @param {Object} urlTemplate underscore templates for meta download urls
- * @param {Object} modelJson data from the model
- * @returns {Object} url and filetype for each meta file
- */
- _renderMetaDownloadUrls : function( urlTemplate, modelJson ){
- return _.map( modelJson.meta_files, function( meta_file ){
- return {
- url : _.template( urlTemplate, { id: modelJson.id, file_type: meta_file.file_type }),
- file_type : meta_file.file_type
- };
- });
- },
-
/** set up js behaviors, event handlers for elements within the given container
* @param {jQuery} $container jq object that contains the elements to process (defaults to this.$el)
*/
@@ -218,8 +156,8 @@
_render_displayButton : function(){
// don't show display if not viewable or not accessible
// (do show if in error, running)
- if( ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NEW )
+ if( ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NEW )
|| ( !this.model.get( 'accessible' ) ) ){
this.displayButton = null;
return null;
@@ -237,7 +175,7 @@
displayBtnData.title = _l( 'Cannot display datasets removed from disk' );
// disable if still uploading
- } else if( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.UPLOAD ){
+ } else if( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.UPLOAD ){
displayBtnData.enabled = false;
displayBtnData.title = _l( 'This dataset must finish uploading before it can be viewed' );
@@ -406,40 +344,40 @@
body.html( '' );
//TODO: not a fan of this dispatch
switch( this.model.get( 'state' ) ){
- case HistoryDatasetAssociation.STATES.NEW :
+ case hdaModel.HistoryDatasetAssociation.STATES.NEW :
this._render_body_new( body );
break;
- case HistoryDatasetAssociation.STATES.NOT_VIEWABLE :
+ case hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE :
this._render_body_not_viewable( body );
break;
- case HistoryDatasetAssociation.STATES.UPLOAD :
+ case hdaModel.HistoryDatasetAssociation.STATES.UPLOAD :
this._render_body_uploading( body );
break;
- case HistoryDatasetAssociation.STATES.PAUSED:
+ case hdaModel.HistoryDatasetAssociation.STATES.PAUSED:
this._render_body_paused( body );
break;
- case HistoryDatasetAssociation.STATES.QUEUED :
+ case hdaModel.HistoryDatasetAssociation.STATES.QUEUED :
this._render_body_queued( body );
break;
- case HistoryDatasetAssociation.STATES.RUNNING :
+ case hdaModel.HistoryDatasetAssociation.STATES.RUNNING :
this._render_body_running( body );
break;
- case HistoryDatasetAssociation.STATES.ERROR :
+ case hdaModel.HistoryDatasetAssociation.STATES.ERROR :
this._render_body_error( body );
break;
- case HistoryDatasetAssociation.STATES.DISCARDED :
+ case hdaModel.HistoryDatasetAssociation.STATES.DISCARDED :
this._render_body_discarded( body );
break;
- case HistoryDatasetAssociation.STATES.SETTING_METADATA :
+ case hdaModel.HistoryDatasetAssociation.STATES.SETTING_METADATA :
this._render_body_setting_metadata( body );
break;
- case HistoryDatasetAssociation.STATES.EMPTY :
+ case hdaModel.HistoryDatasetAssociation.STATES.EMPTY :
this._render_body_empty( body );
break;
- case HistoryDatasetAssociation.STATES.FAILED_METADATA :
+ case hdaModel.HistoryDatasetAssociation.STATES.FAILED_METADATA :
this._render_body_failed_metadata( body );
break;
- case HistoryDatasetAssociation.STATES.OK :
+ case hdaModel.HistoryDatasetAssociation.STATES.OK :
this._render_body_ok( body );
break;
default:
@@ -591,27 +529,44 @@
* @fires body-expanded when a body has been expanded
* @fires body-collapsed when a body has been collapsed
*/
- toggleBodyVisibility : function( event, expanded ){
+ toggleBodyVisibility : function( event, expand ){
var hdaView = this;
- this.expanded = ( expanded === undefined )?( !this.body.is( ':visible' ) ):( expanded );
- //this.log( 'toggleBodyVisibility, expanded:', expanded, '$body:', $body );
+ expand = ( expand === undefined )?( !this.body.is( ':visible' ) ):( expand );
+ if( expand ){
+ if( this.model.inReadyState() && !this.model.hasDetails() ){
+ var xhr = this.model.fetch();
+ xhr.done( function( model ){
+ hdaView.expandBody();
+ });
+ } else {
+ this.expandBody();
+ }
+ } else {
+ this.collapseBody();
+ }
+ },
- if( this.expanded ){
- hdaView._render_body_html( hdaView.body );
- this.body.slideDown( 'fast', function(){
- hdaView.trigger( 'body-expanded', hdaView.model.get( 'id' ) );
- });
- } else {
- this.body.slideUp( 'fast', function(){
- hdaView.trigger( 'body-collapsed', hdaView.model.get( 'id' ) );
- });
- }
+ expandBody : function(){
+ var hdaView = this;
+ hdaView._render_body_html( hdaView.body );
+ this.body.slideDown( hdaView.fxSpeed, function(){
+ hdaView.expanded = true;
+ hdaView.trigger( 'body-expanded', hdaView.model.get( 'id' ) );
+ });
+ },
+
+ collapseBody : function(){
+ var hdaView = this;
+ this.body.slideUp( hdaView.fxSpeed, function(){
+ hdaView.expanded = false;
+ hdaView.trigger( 'body-collapsed', hdaView.model.get( 'id' ) );
+ });
},
// ......................................................................... DELETION
remove : function( callback ){
var hdaView = this;
- this.$el.fadeOut( 'fast', function(){
+ this.$el.fadeOut( hdaView.fxSpeed, function(){
hdaView.$el.remove();
hdaView.off();
if( callback ){ callback(); }
@@ -638,6 +593,6 @@
};
//==============================================================================
-//return {
-// HDABaseView : HDABaseView,
-//};});
+return {
+ HDABaseView : HDABaseView,
+};});
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a static/scripts/mvc/dataset/hda-edit.js
--- a/static/scripts/mvc/dataset/hda-edit.js
+++ b/static/scripts/mvc/dataset/hda-edit.js
@@ -1,6 +1,7 @@
-//define([
-// "../mvc/base-mvc"
-//], function(){
+define([
+ "mvc/dataset/hda-model",
+ "mvc/dataset/hda-base"
+], function( hdaModel, hdaBase ){
//==============================================================================
/** @class Editing view for HistoryDatasetAssociation.
* @name HDAEditView
@@ -10,7 +11,7 @@
* @borrows LoggableMixin#log as #log
* @constructs
*/
-var HDAEditView = HDABaseView.extend( LoggableMixin ).extend(
+var HDAEditView = hdaBase.HDABaseView.extend( LoggableMixin ).extend(
/** @lends HDAEditView.prototype */{
// ......................................................................... SET UP
@@ -22,7 +23,8 @@
* @see HDABaseView#initialize
*/
initialize : function( attributes ){
- HDABaseView.prototype.initialize.call( this, attributes );
+ hdaBase.HDABaseView.prototype.initialize.call( this, attributes );
+ this.hasUser = attributes.hasUser;
/** list of rendering functions for the default, primary icon-buttons. */
this.defaultPrimaryActionButtonRenderers = [
@@ -37,33 +39,8 @@
* @param {jQuery} $container jq object that contains the elements to process (defaults to this.$el)
*/
_setUpBehaviors : function( $container ){
- //TODO: ideally this would be a DELETE call to the api
- // using purge async for now
- HDABaseView.prototype._setUpBehaviors.call( this, $container );
-
- // use purge_async with an ajax call
- var hdaView = this,
- purge_url = this.urls.purge,
- purge_link = $container.find( '#historyItemPurger-' + this.model.get( 'id' ) );
- if( purge_link ){
- //TODO: remove href from template
- purge_link.attr( 'href', [ "javascript", "void(0)" ].join( ':' ) );
- purge_link.click( function( event ){
- //TODO??: confirm?
- var xhr = jQuery.ajax( purge_url );
- xhr.success( function( message, status, responseObj ){
- hdaView.model.set( 'purged', true );
- hdaView.trigger( 'purged', hdaView );
- });
- xhr.error( function( error, status, message ){
- //TODO: Exception messages are hidden within error page
- //!NOTE: that includes the 'Removal of datasets by users is not allowed in this Galaxy instance.'
- view.trigger( 'error',
- hdaView, xhr, { url: purge_url }, _l( "Unable to purge this dataset" ) );
- });
- });
- }
- //TODO: same with undelete_async
+ hdaBase.HDABaseView.prototype._setUpBehaviors.call( this, $container );
+ //var hdaView = this;
},
// ......................................................................... RENDER WARNINGS
@@ -74,7 +51,7 @@
*/
_render_warnings : function(){
// jQ errs on building dom with whitespace - if there are no messages, trim -> ''
- return $( jQuery.trim( HDABaseView.templates.messages(
+ return $( jQuery.trim( hdaBase.HDABaseView.templates.messages(
_.extend( this.model.toJSON(), { urls: this.urls } )
)));
},
@@ -101,9 +78,9 @@
// don't show edit while uploading, in-accessible
// DO show if in error (ala previous history panel)
//TODO??: not viewable/accessible are essentially the same (not viewable set from accessible)
- if( ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NEW )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.UPLOAD )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
+ if( ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NEW )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.UPLOAD )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
|| ( !this.model.get( 'accessible' ) ) ){
this.editButton = null;
return null;
@@ -138,44 +115,26 @@
_render_deleteButton : function(){
// don't show delete if...
//TODO??: not viewable/accessible are essentially the same (not viewable set from accessible)
- if( ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NEW )
- || ( this.model.get( 'state' ) === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
+ if( ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NEW )
+ || ( this.model.get( 'state' ) === hdaModel.HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
|| ( !this.model.get( 'accessible' ) ) ){
this.deleteButton = null;
return null;
}
var self = this,
+ id = 'historyItemDeleter-' + self.model.get( 'id' ),
delete_url = self.urls[ 'delete' ],
deleteBtnData = {
- title : _l( 'Delete' ),
- href : delete_url,
- id : 'historyItemDeleter-' + this.model.get( 'id' ),
- icon_class : 'delete',
- on_click : function() {
- // Delete the dataset on the server and update HDA + view depending on success/failure.
- // FIXME: when HDA-delete is implemented in the API, can call set(), then save directly
- // on the model.
- $.ajax({
- url: delete_url,
- type: 'POST',
- error: function() {
- // Something went wrong, so show HDA again.
- // TODO: an error notification would be good.
- self.trigger( 'error', self, null, null, { url: delete_url }, _l( 'deletion failed' ) );
- self.$el.show();
- },
- success: function() {
- // FIXME: setting model attribute causes re-rendering, which is unnecessary.
- //self.$el.remove();
-
- self.model.set({ deleted: true });
- }
- });
-
- // Return false so that anchor action (page reload) does not happen.
- //return false;
- }
+ title : _l( 'Delete' ),
+ href : delete_url,
+ id : id,
+ icon_class : 'delete',
+ on_click : function() {
+ // ...bler... tooltips being left behind in DOM (hover out never called on deletion)
+ self.$el.find( '.menu-button.delete' ).trigger( 'mouseout' );
+ self.model[ 'delete' ]();
+ }
};
if( this.model.get( 'deleted' ) || this.model.get( 'purged' ) ){
deleteBtnData = {
@@ -202,7 +161,7 @@
//TODO: use HDABaseView and select/replace base on this switch
_.extend( modelData, { dbkey_unknown_and_editable : true });
}
- return HDABaseView.templates.hdaSummary( modelData );
+ return hdaBase.HDABaseView.templates.hdaSummary( modelData );
},
// ......................................................................... primary actions
@@ -210,7 +169,7 @@
* @returns {jQuery} rendered DOM
*/
_render_errButton : function(){
- if( this.model.get( 'state' ) !== HistoryDatasetAssociation.STATES.ERROR ){
+ if( this.model.get( 'state' ) !== hdaModel.HistoryDatasetAssociation.STATES.ERROR ){
this.errButton = null;
return null;
}
@@ -378,8 +337,7 @@
//TODO: these should be a sub-MV
_render_tagButton : function(){
//TODO: check for User
- if( !( this.model.hasData() )
- || ( !this.urls.tags.get ) ){
+ if( !this.hasUser || !this.urls.tags.get ){
this.tagButton = null;
return null;
}
@@ -399,8 +357,7 @@
//TODO: these should be a sub-MV
_render_annotateButton : function(){
//TODO: check for User
- if( !( this.model.hasData() )
- || ( !this.urls.annotation.get ) ){
+ if( !this.hasUser || !this.urls.annotation.get ){
this.annotateButton = null;
return null;
}
@@ -417,8 +374,8 @@
/** Render area to display tags.
* @returns {jQuery} rendered DOM
*/
- //TODO: into sub-MV
- //TODO: check for User
+//TODO: into sub-MV
+//TODO: check for User
_render_tagArea : function(){
if( !this.urls.tags.set ){ return null; }
//TODO: move to mvc/tags.js
@@ -430,8 +387,8 @@
/** Render area to display annotation.
* @returns {jQuery} rendered DOM
*/
- //TODO: into sub-MV
- //TODO: check for User
+//TODO: into sub-MV
+//TODO: check for User
_render_annotationArea : function(){
if( !this.urls.annotation.get ){ return null; }
//TODO: move to mvc/annotations.js
@@ -447,7 +404,7 @@
* @see HDABaseView#_render_body_error
*/
_render_body_error : function( parent ){
- HDABaseView.prototype._render_body_error.call( this, parent );
+ hdaBase.HDABaseView.prototype._render_body_error.call( this, parent );
var primaryActions = parent.find( '#primary-actions-' + this.model.get( 'id' ) );
primaryActions.prepend( this._render_errButton() );
},
@@ -498,11 +455,21 @@
/** event map */
events : {
'click .historyItemTitle' : 'toggleBodyVisibility',
+ 'click .historyItemUndelete' : function( ev ){ this.model.undelete(); return false; },
+ 'click .historyItemUnhide' : function( ev ){ this.model.unhide(); return false; },
+ 'click .historyItemPurge' : 'confirmPurge',
+
'click a.icon-button.tags' : 'loadAndDisplayTags',
'click a.icon-button.annotate' : 'loadAndDisplayAnnotation'
},
// ......................................................................... STATE CHANGES / MANIPULATION
+ confirmPurge : function _confirmPurge( ev ){
+ //TODO: confirm dialog
+ this.model.purge({ url: this.urls.purge });
+ return false;
+ },
+
/** Find the tag area and, if initial: load the html (via ajax) for displaying them; otherwise, unhide/hide
*/
//TODO: into sub-MV
@@ -523,30 +490,29 @@
url: this.urls.tags.get,
error: function( xhr, status, error ){
view.log( "Tagging failed", xhr, status, error );
- view.trigger( 'error', view, xhr, { url: view.urls.tags.get }, _l( "Tagging failed" ) );
+ view.trigger( 'error', view, xhr, {}, _l( "Tagging failed" ) );
},
success: function(tag_elt_html) {
tagElt.html(tag_elt_html);
tagElt.find("[title]").tooltip();
- tagArea.slideDown("fast");
+ tagArea.slideDown( view.fxSpeed );
}
});
} else {
// Tag element is filled; show.
- tagArea.slideDown("fast");
+ tagArea.slideDown( view.fxSpeed );
}
} else {
// Hide.
- tagArea.slideUp("fast");
+ tagArea.slideUp( view.fxSpeed );
}
return false;
},
/** Find the annotation area and, if initial: load the html (via ajax) for displaying them; otherwise, unhide/hide
*/
- //TODO: into sub-MV
loadAndDisplayAnnotation : function( event ){
- //TODO: this is a drop in from history.mako - should use MV as well
+//TODO: this is a drop in from history.mako - should use MV as well
this.log( this + '.loadAndDisplayAnnotation', event );
var view = this,
annotationArea = this.$el.find( '.annotation-area' ),
@@ -559,10 +525,9 @@
// Need to fill annotation element.
$.ajax({
url: this.urls.annotation.get,
- error: function( xhr, status, message ){
- view.log( "Annotation failed", xhr, status, message );
- view.trigger( 'error',
- view, xhr, { url: view.urls.annotation.get }, _l( "Annotation failed" ) );
+ error: function(){
+ view.log( "Annotation failed", xhr, status, error );
+ view.trigger( 'error', view, xhr, {}, _l( "Annotation failed" ) );
},
success: function( htmlFromAjax ){
if( htmlFromAjax === "" ){
@@ -576,16 +541,16 @@
setAnnotationUrl,
"new_annotation", 18, true, 4
);
- annotationArea.slideDown("fast");
+ annotationArea.slideDown( view.fxSpeed );
}
});
} else {
- annotationArea.slideDown("fast");
+ annotationArea.slideDown( view.fxSpeed );
}
} else {
// Hide.
- annotationArea.slideUp("fast");
+ annotationArea.slideUp( view.fxSpeed );
}
return false;
},
@@ -712,6 +677,6 @@
//==============================================================================
-//return {
-// HDAView : HDAView,
-//};});
+return {
+ HDAEditView : HDAEditView,
+};});
diff -r 6882fa888d10b469524669325a547a2c0f6c7e41 -r 4f1c25230dd009efd1f04f8d7a74d83733f8b75a static/scripts/mvc/dataset/hda-model.js
--- a/static/scripts/mvc/dataset/hda-model.js
+++ b/static/scripts/mvc/dataset/hda-model.js
@@ -1,6 +1,5 @@
-//define([
-// "../mvc/base-mvc"
-//], function(){
+define([
+], function(){
//==============================================================================
/** @class (HDA) model for a Galaxy dataset
* related to a history.
@@ -34,6 +33,13 @@
name : '(unnamed dataset)',
// one of HistoryDatasetAssociation.STATES
state : 'new',
+
+ deleted : false,
+ visible : true,
+
+ accessible : true,
+ purged : false,
+
// sniffed datatype (sam, tabular, bed, etc.)
data_type : null,
// size in bytes
@@ -44,37 +50,67 @@
meta_files : [],
misc_blurb : '',
- misc_info : '',
-
- deleted : false,
- purged : false,
- visible : true,
- accessible : true
+ misc_info : ''
},
/** fetch location of this history in the api */
urlRoot: 'api/histories/',
url : function(){
- //TODO: get this via url router
return this.urlRoot + this.get( 'history_id' ) + '/contents/' + this.get( 'id' );
- //TODO: this breaks on save()
},
+ urls : function(){
+ var id = this.get( 'id' );
+ if( !id ){ return {}; }
+ var urls = {
+ 'delete' : '/datasets/' + id + '/delete_async',
+ 'purge' : '/datasets/' + id + '/purge_async',
+ 'unhide' : '/datasets/' + id + '/unhide',
+ 'undelete' : '/datasets/' + id + '/undelete',
+
+ 'display' : '/datasets/' + id + '/display/?preview=True',
+ 'download' : '/datasets/' + id + '/display?to_ext=' + this.get( 'file_ext' ),
+ 'edit' : '/datasets/' + id + '/edit',
+ 'report_error': '/dataset/errors?id=' + id,
+ 'rerun' : '/tool_runner/rerun?id=' + id,
+ 'show_params': '/datasets/' + id + '/show_params',
+ 'visualization': '/visualization',
+
+ 'annotation': { 'get': '/dataset/get_annotation_async?id=' + id,
+ 'set': '/dataset/annotate_async?id=' + id },
+ 'tags' : { 'get': '/tag/get_tagging_elt_async?item_id=' + id + '&item_class=HistoryDatasetAssociation',
+ 'set': '/tag/retag?item_id=' + id + '&item_class=HistoryDatasetAssociation' }
+ };
+ //'meta_download': '/dataset/get_metadata_file?hda_id=%3C%25%3D+id+%25%3E&metadata_name=%3C%25%3D+file_type+%25%3E',
+ var meta_files = this.get( 'meta_files' );
+ if( meta_files ){
+ urls.meta_download = _.map( meta_files, function( meta_file ){
+ return {
+ //url : _.template( urlTemplate, { id: modelJson.id, file_type: meta_file.file_type }),
+ url : '/dataset/get_metadata_file?hda_id=' + id + '&metadata_name=' + meta_file.file_type,
+ file_type : meta_file.file_type
+ };
+ });
+ }
+ return urls;
+ },
+
/** Set up the model, determine if accessible, bind listeners
* @see Backbone.Model#initialize
*/
- //TODO:? use initialize (or validate) to check purged AND deleted -> purged XOR deleted
- initialize : function(){
+ initialize : function( data ){
this.log( this + '.initialize', this.attributes );
this.log( '\tparent history_id: ' + this.get( 'history_id' ) );
- // (curr) only handles changing state of non-accessible hdas to STATES.NOT_VIEWABLE
//!! this state is not in trans.app.model.Dataset.states - set it here -
- //TODO: change to server side.
if( !this.get( 'accessible' ) ){
this.set( 'state', HistoryDatasetAssociation.STATES.NOT_VIEWABLE );
}
+ this._setUpListeners();
+ },
+
+ _setUpListeners : function(){
// if the state has changed and the new state is a ready state, fire an event
this.on( 'change:state', function( currModel, newState ){
this.log( this + ' has changed state:', currModel, newState );
@@ -82,16 +118,9 @@
this.trigger( 'state:ready', currModel, newState, this.previous( 'state' ) );
}
});
-
- // debug on change events
- //this.on( 'change', function( currModel, changedList ){
- // this.log( this + ' has changed:', currModel, changedList );
- //});
- //this.bind( 'all', function( event ){
- // this.log( this + '', arguments );
- //});
},
+ // ........................................................................ common queries
/** Is this hda deleted or purged?
*/
isDeletedOrPurged : function(){
@@ -117,24 +146,21 @@
return isVisible;
},
+ hidden : function(){
+ return !this.get( 'visible' );
+ },
+
/** Is this HDA in a 'ready' state; where 'Ready' states are states where no
* processing (for the ds) is left to do on the server.
- * Currently: NEW, OK, EMPTY, FAILED_METADATA, NOT_VIEWABLE, DISCARDED,
- * and ERROR
*/
inReadyState : function(){
- var state = this.get( 'state' );
- //TODO: to list inclusion test
- //TODO: class level readyStates list
- return (
- this.isDeletedOrPurged()
- || ( state === HistoryDatasetAssociation.STATES.OK )
- || ( state === HistoryDatasetAssociation.STATES.EMPTY )
- || ( state === HistoryDatasetAssociation.STATES.FAILED_METADATA )
- || ( state === HistoryDatasetAssociation.STATES.NOT_VIEWABLE )
- || ( state === HistoryDatasetAssociation.STATES.DISCARDED )
- || ( state === HistoryDatasetAssociation.STATES.ERROR )
- );
+ var ready = _.contains( HistoryDatasetAssociation.READY_STATES, this.get( 'state' ) );
+ return ( this.isDeletedOrPurged() || ready );
+ },
+
+ hasDetails : function(){
+ //?? this may not be reliable
+ return _.has( this.attributes, 'genome_build' );
},
/** Convenience function to match hda.has_data.
@@ -144,6 +170,64 @@
return ( this.get( 'file_size' ) > 0 );
},
+ // ........................................................................ ajax
+ 'delete' : function _delete( options ){
+ return this.save( { deleted: true }, options );
+ },
+ undelete : function _undelete( options ){
+ return this.save( { deleted: false }, options );
+ },
+
+ hide : function _hide( options ){
+ return this.save( { visible: false }, options );
+ },
+ unhide : function _uhide( options ){
+ return this.save( { visible: true }, options );
+ },
+
+ purge : function _purge( options ){
+ //TODO: ideally this would be a DELETE call to the api
+ // using purge async for now
+ var hda = this,
+ xhr = jQuery.ajax( options );
+ xhr.done( function( message, status, responseObj ){
+ hda.set( 'purged', true );
+ });
+ xhr.fail( function( xhr, status, message ){
+ // Exception messages are hidden within error page including: '...not allowed in this Galaxy instance.'
+ // unbury and re-add to xhr
+ var error = _l( "Unable to purge this dataset" );
+ var messageBuriedInUnfortunatelyFormattedError = ( 'Removal of datasets by users '
+ + 'is not allowed in this Galaxy instance' );
+ if( xhr.responseJSON && xhr.responseJSON.error ){
+ error = xhr.responseJSON.error;
+ } else if( xhr.responseText.indexOf( messageBuriedInUnfortunatelyFormattedError ) !== -1 ){
+ error = messageBuriedInUnfortunatelyFormattedError;
+ }
+ xhr.responseText = error;
+ hda.trigger( 'error', hda, xhr, options, _l( error ), { error: error } );
+ });
+ },
+
+ // ........................................................................ sorting/filtering
+ searchKeys : [
+ 'name', 'file_ext', 'genome_build', 'misc_blurb', 'misc_info', 'annotation', 'tags'
+ ],
+
+ search : function( searchFor ){
+ var model = this;
+ searchFor = searchFor.toLowerCase();
+ return _.filter( this.searchKeys, function( key ){
+ var attr = model.get( key );
+ return ( _.isString( attr ) && attr.toLowerCase().indexOf( searchFor ) !== -1 );
+ });
+ },
+
+ matches : function( matchesWhat ){
+ return !!this.search( matchesWhat ).length;
+ },
+
+ // ........................................................................ misc
/** String representation
*/
toString : function(){
@@ -165,8 +249,6 @@
UPLOAD : 'upload',
/** the job that will produce the dataset queued in the runner */
QUEUED : 'queued',
- /** the job that will produce the dataset paused */
- PAUSED : 'paused',
/** the job that will produce the dataset is running */
RUNNING : 'running',
/** metadata for the dataset is being discovered/set */
@@ -180,6 +262,8 @@
/** has successfully completed running */
OK : 'ok',
+ /** the job that will produce the dataset paused */
+ PAUSED : 'paused',
/** metadata discovery/setting failed or errored (but otherwise ok) */
FAILED_METADATA : 'failed_metadata',
/** not accessible to the current user (i.e. due to permissions) */
@@ -190,6 +274,24 @@
ERROR : 'error'
};
+HistoryDatasetAssociation.READY_STATES = [
+ HistoryDatasetAssociation.STATES.NEW,
+ HistoryDatasetAssociation.STATES.OK,
+ HistoryDatasetAssociation.STATES.EMPTY,
+ HistoryDatasetAssociation.STATES.PAUSED,
+ HistoryDatasetAssociation.STATES.FAILED_METADATA,
+ HistoryDatasetAssociation.STATES.NOT_VIEWABLE,
+ HistoryDatasetAssociation.STATES.DISCARDED,
+ HistoryDatasetAssociation.STATES.ERROR
+];
+
+HistoryDatasetAssociation.NOT_READY_STATES = [
+ HistoryDatasetAssociation.STATES.UPLOAD,
+ HistoryDatasetAssociation.STATES.QUEUED,
+ HistoryDatasetAssociation.STATES.RUNNING,
+ HistoryDatasetAssociation.STATES.SETTING_METADATA
+];
+
//==============================================================================
/** @class Backbone collection of (HDA) models
*
@@ -204,83 +306,35 @@
///** logger used to record this.log messages, commonly set to console */
//// comment this out to suppress log output
//logger : console,
+ urlRoot : '/api/histories',
+ url : function(){
+ return this.urlRoot + '/' + this.historyId + '/contents';
+ },
/** Set up.
* @see Backbone.Collection#initialize
*/
- initialize : function(){
- //this.bind( 'all', function( event ){
- // this.log( this + '', arguments );
- //});
+ initialize : function( models, options ){
+ options = options || {};
+ this.historyId = options.historyId;
+ this._setUpListeners();
},
+ _setUpListeners : function(){
+ },
+
+ // ........................................................................ common queries
/** Get the ids of every hda in this collection
- * @returns array of encoded ids
+ * @returns array of encoded ids
*/
ids : function(){
return this.map( function( hda ){ return hda.id; });
},
- /** Get the hda with the given hid
- * @param {Int} hid the hid to search for
- * @returns {HistoryDatasetAssociation} the hda with the given hid or undefined if not found
- */
- getByHid : function( hid ){
- return _.first( this.filter( function( hda ){ return hda.get( 'hid' ) === hid; }) );
- },
-
- /** If the given hid is in the collection, return it's index. If not, return the insertion point it would need.
- * NOTE: assumes hids are unique and valid
- * @param {Int} hid the hid to find or create. If hid is 0, null, undefined: return the last hid + 1
- * @returns the collection index of the existing hda or an insertion point if it doesn't exist
- */
- hidToCollectionIndex : function( hid ){
- // if the hid is 0, null, undefined: assume a request for a new hid (return the last index)
- if( !hid ){
- return this.models.length;
- }
-
- var endingIndex = this.models.length - 1;
- //TODO: prob. more efficient to cycle backwards through these (assuming ordered by hid)
- for( var i=endingIndex; i>=0; i-- ){
- var hdaHid = this.at( i ).get( 'hid' );
- //this.log( i, 'hdaHid:', hdaHid );
- if( hdaHid === hid ){
- //this.log( '\t match:', hdaHid, hid, ' returning:', i );
- return i;
- }
- if( hdaHid < hid ){
- //this.log( '\t past it, returning:', ( i + 1 ) );
- return i + 1;
- }
- }
- return null;
- },
-
- /** Get every 'shown' hda in this collection based on show_deleted/hidden
- * @param {Boolean} show_deleted are we showing deleted hdas?
- * @param {Boolean} show_hidden are we showing hidden hdas?
- * @returns array of hda models
- * @see HistoryDatasetAssociation#isVisible
- */
- getVisible : function( show_deleted, show_hidden ){
- return this.filter( function( item ){ return item.isVisible( show_deleted, show_hidden ); });
- },
-
- /** For each possible hda state, get an array of all hda ids in that state
- * @returns a map of states -> hda ids
- * @see HistoryDatasetAssociation#STATES
- */
- getStateLists : function(){
- var stateLists = {};
- _.each( _.values( HistoryDatasetAssociation.STATES ), function( state ){
- stateLists[ state ] = [];
+ notReady : function(){
+ return this.filter( function( hda ){
+ return !hda.inReadyState();
});
- //NOTE: will err on unknown state
- this.each( function( item ){
- stateLists[ item.get( 'state' ) ].push( item.get( 'id' ) );
- });
- return stateLists;
},
/** Get the id of every hda in this collection not in a 'ready' state (running).
@@ -297,26 +351,55 @@
return idList;
},
- /** Update (fetch) the data of the hdas with the given ids.
- * @param {String[]} ids an array of hda ids to update
- * @returns {HistoryDatasetAssociation[]} hda models that were updated
- * @see HistoryDatasetAssociation#fetch
+ /** Get the hda with the given hid
+ * @param {Int} hid the hid to search for
+ * @returns {HistoryDatasetAssociation} the hda with the given hid or undefined if not found
*/
- update : function( ids ){
- this.log( this + 'update:', ids );
+ getByHid : function( hid ){
+ return _.first( this.filter( function( hda ){ return hda.get( 'hid' ) === hid; }) );
+ },
- if( !( ids && ids.length ) ){ return []; }
+ /** Get every 'shown' hda in this collection based on show_deleted/hidden
+ * @param {Boolean} show_deleted are we showing deleted hdas?
+ * @param {Boolean} show_hidden are we showing hidden hdas?
+ * @returns array of hda models
+ * @see HistoryDatasetAssociation#isVisible
+ */
+ getVisible : function( show_deleted, show_hidden ){
+ return this.filter( function( item ){ return item.isVisible( show_deleted, show_hidden ); });
+ },
- var collection = this,
- updatedHdas = null;
- _.each( ids, function( id, index ){
- var hda = collection.get( id );
- if( hda ){
- hda.fetch();
- updatedHdas.push( hda );
- }
+ // ........................................................................ ajax
+ fetchAllDetails : function(){
+ return this.fetch({ data : { details : 'all' } });
+ },
+
+ // ........................................................................ sorting/filtering
+ matches : function( matchesWhat ){
+ return this.filter( function( hda ){
+ return hda.matches( matchesWhat );
});
- return updatedHdas;
+ },
+
+ // ........................................................................ misc
+ set : function( models, options ){
+ // arrrrrrrrrrrrrrrrrg...
+ // override to get a correct/smarter merge when incoming data is partial (e.g. stupid backbone)
+ // w/o this partial models from the server will fill in missing data with model defaults
+ // and overwrite existing data on the client
+ // see Backbone.Collection.set and _prepareModel
+ var collection = this;
+ models = _.map( models, function( model ){
+ var existing = collection.get( model.id );
+ if( !existing ){ return model; }
+
+ // merge the models _BEFORE_ calling the superclass version
+ var merged = existing.toJSON();
+ _.extend( merged, model );
+ return merged;
+ });
+ // now call superclass when the data is filled
+ Backbone.Collection.prototype.set.call( this, models, options );
},
/** String representation. */
@@ -326,7 +409,7 @@
});
//==============================================================================
-//return {
-// HistoryDatasetAssociation : HistoryDatasetAssociation,
-// HDACollection : HDACollection,
-//};});
+return {
+ HistoryDatasetAssociation : HistoryDatasetAssociation,
+ HDACollection : HDACollection
+};});
This diff is so big that we needed to truncate the remainder.
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.
1
0
commit/galaxy-central: dannon: Datatypes controller should allow anonymous access.
by commits-noreply@bitbucket.org 21 Oct '13
by commits-noreply@bitbucket.org 21 Oct '13
21 Oct '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/81880a04e6e7/
Changeset: 81880a04e6e7
Branch: next-stable
User: dannon
Date: 2013-10-21 22:16:01
Summary: Datatypes controller should allow anonymous access.
Affected #: 1 file
diff -r 000d11c7ce7e6125998d7095a247774a150c120e -r 81880a04e6e79d944a6d9c225b36417114cd38ec lib/galaxy/webapps/galaxy/api/datatypes.py
--- a/lib/galaxy/webapps/galaxy/api/datatypes.py
+++ b/lib/galaxy/webapps/galaxy/api/datatypes.py
@@ -4,13 +4,12 @@
from galaxy import web
from galaxy.web.base.controller import BaseAPIController
-from galaxy.datatypes.registry import Registry
import logging
log = logging.getLogger( __name__ )
class DatatypesController( BaseAPIController ):
- @web.expose_api
+ @web.expose_api_anonymous
def index( self, trans, **kwd ):
"""
GET /api/datatypes
@@ -18,8 +17,7 @@
"""
try:
return trans.app.datatypes_registry.upload_file_formats
-
except Exception, exception:
log.error( 'could not get datatypes: %s', str( exception ), exc_info=True )
trans.response.status = 500
- return { 'error': str( exception ) }
\ No newline at end of file
+ return { 'error': str( exception ) }
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.
1
0