galaxy-commits
Threads by month
- ----- 2025 -----
- 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
May 2013
- 1 participants
- 218 discussions

commit/galaxy-central: greg: Fix tool shed functional test I broke.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/af7b3b73130b/
Changeset: af7b3b73130b
User: greg
Date: 2013-05-02 22:44:49
Summary: Fix tool shed functional test I broke.
Affected #: 1 file
diff -r 1528410bbe976f425df16de8ee81c49c5a0432da -r af7b3b73130b9288112fd06d2cecbcfe649703c5 test/tool_shed/functional/test_0000_basic_repository_features.py
--- a/test/tool_shed/functional/test_0000_basic_repository_features.py
+++ b/test/tool_shed/functional/test_0000_basic_repository_features.py
@@ -99,7 +99,7 @@
tool_metadata_strings_displayed=tool_metadata_strings_displayed,
tool_page_strings_displayed=tool_page_strings_displayed )
self.check_repository_metadata( repository, tip_only=False )
- self.browse_repository( repository, strings_displayed=[ 'Browse %s revision' % repository.name, '(repository tip)' ] )
+ self.browse_repository( repository, strings_displayed=[ "Repository '%s' revision" % repository.name, '(repository tip)' ] )
self.display_repository_clone_page( common.test_user_1_name,
repository_name,
strings_displayed=[ 'Uploaded filtering 1.1.0', latest_changeset_revision ] )
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: natefoo: Delete/stop jobs when a history is deleted.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/1528410bbe97/
Changeset: 1528410bbe97
User: natefoo
Date: 2013-05-02 21:50:00
Summary: Delete/stop jobs when a history is deleted.
Affected #: 1 file
diff -r 3044a594eef9868f41d90b43f1c993def91abe9e -r 1528410bbe976f425df16de8ee81c49c5a0432da lib/galaxy/webapps/galaxy/controllers/history.py
--- a/lib/galaxy/webapps/galaxy/controllers/history.py
+++ b/lib/galaxy/webapps/galaxy/controllers/history.py
@@ -562,6 +562,12 @@
history.purged = True
self.sa_session.add( history )
self.sa_session.flush()
+ for hda in history.datasets:
+ job = hda.creating_job_associations[0].job
+ if job.history_id == history.id and job.state in [ trans.app.model.Job.states.QUEUED, trans.app.model.Job.states.RUNNING, trans.app.model.Job.states.NEW ]:
+ # No need to check other outputs since the job's parent history is this history
+ job.mark_deleted( trans.app.config.track_jobs_in_database )
+ trans.app.job_manager.job_stop_queue.put( job.id )
# Regardless of whether it was previously deleted, we make a new history active
trans.new_history()
return trans.show_ok_message( "History deleted, a new history is active", refresh_frames=['history'] )
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: dan: Display error to user when genomespace file browser tool is used with no imported datasets.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/3044a594eef9/
Changeset: 3044a594eef9
User: dan
Date: 2013-05-02 21:46:06
Summary: Display error to user when genomespace file browser tool is used with no imported datasets.
Affected #: 1 file
diff -r 8d8368ab03ff95c2aa88861ed0284cf48ca73631 -r 3044a594eef9868f41d90b43f1c993def91abe9e tools/genomespace/genomespace_file_browser.py
--- a/tools/genomespace/genomespace_file_browser.py
+++ b/tools/genomespace/genomespace_file_browser.py
@@ -113,6 +113,10 @@
if name.startswith( file_url_prefix ):
name = name[len( file_url_prefix ):]
file_numbers.append( int( name ) )
+ if not file_numbers:
+ if output_filename:
+ open( output_filename, 'wb' ) #erase contents of file
+ raise Exception( "You must select at least one file to import into Galaxy." )
file_numbers.sort()
used_filenames = []
for file_num in file_numbers:
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: greg: Re-add the ability to preview and install repositories from the Valid repositories grid in the tool shed.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/8d8368ab03ff/
Changeset: 8d8368ab03ff
User: greg
Date: 2013-05-02 21:44:05
Summary: Re-add the ability to preview and install repositories from the Valid repositories grid in the tool shed.
Affected #: 1 file
diff -r d2a4a4e4165058439ad0ffb09003f8d57a19233e -r 8d8368ab03ff95c2aa88861ed0284cf48ca73631 lib/tool_shed/grids/repository_grids.py
--- a/lib/tool_shed/grids/repository_grids.py
+++ b/lib/tool_shed/grids/repository_grids.py
@@ -1424,7 +1424,7 @@
columns = [
RepositoryGrid.NameColumn( "Name",
key="name",
- attach_popup=False ),
+ attach_popup=True ),
RepositoryGrid.DescriptionColumn( "Synopsis",
key="description",
attach_popup=False ),
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
64 new commits in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/d128613ae7c9/
Changeset: d128613ae7c9
User: dannon
Date: 2013-04-18 21:35:00
Summary: Postgres migrations successful, model updated
Affected #: 145 files
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 eggs.ini
--- a/eggs.ini
+++ b/eggs.ini
@@ -28,6 +28,7 @@
simplejson = 2.1.1
threadframe = 0.2
guppy = 0.1.8
+SQLAlchemy = 0.7.9
; msgpack_python = 0.2.4
[eggs:noplatform]
@@ -52,11 +53,10 @@
python_openid = 2.2.5
python_daemon = 1.5.5
Routes = 1.12.3
-SQLAlchemy = 0.5.6
-sqlalchemy_migrate = 0.5.4
+sqlalchemy_migrate = 0.7.2
ssh = 1.7.14
SVGFig = 1.1.6
-Tempita = 0.1
+Tempita = 0.5.1
twill = 0.9
WebError = 0.8a
WebHelpers = 0.2
@@ -75,7 +75,6 @@
MySQL_python = _5.1.41_static
bx_python = _7b95ff194725
GeneTrack = _dev_48da9e998f0caf01c5be731e926f4b0481f658f0
-SQLAlchemy = _dev_r6498
pysam = _kanwei_b10f6e722e9a
; dependency source urls, necessary for scrambling. for an explanation, see
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/datatypes/assembly.py
--- a/lib/galaxy/datatypes/assembly.py
+++ b/lib/galaxy/datatypes/assembly.py
@@ -5,14 +5,14 @@
"""
import data
+import logging
+import os
+import re
+import sys
from galaxy.datatypes import sequence
-import logging, os, sys, time, tempfile, shutil, string, glob, re
-import galaxy.model
-from galaxy.datatypes import metadata
+from galaxy.datatypes.images import Html
from galaxy.datatypes.metadata import MetadataElement
-from galaxy import util
-from galaxy.datatypes.images import Html
-from sniff import *
+
log = logging.getLogger(__name__)
@@ -174,7 +174,6 @@
gen_msg = ''
try:
efp = dataset.extra_files_path
- flist = os.listdir(efp)
log_path = os.path.join(efp,'Log')
f = open(log_path,'r')
log_content = f.read(1000)
@@ -223,5 +222,5 @@
self.regenerate_primary_file(dataset)
if __name__ == '__main__':
- import doctest, sys
+ import doctest
doctest.testmod(sys.modules[__name__])
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/datatypes/binary.py
--- a/lib/galaxy/datatypes/binary.py
+++ b/lib/galaxy/datatypes/binary.py
@@ -2,18 +2,25 @@
Binary classes
"""
-import data, logging, binascii
+
+import binascii
+import data
+import gzip
+import logging
+import os
+import shutil
+import struct
+import subprocess
+import tempfile
+
+from galaxy import eggs
+eggs.require( "bx-python" )
+
+from bx.seq.twobit import TWOBIT_MAGIC_NUMBER, TWOBIT_MAGIC_NUMBER_SWAP, TWOBIT_MAGIC_SIZE
+
+from galaxy.datatypes import metadata
from galaxy.datatypes.metadata import MetadataElement
-from galaxy.datatypes import metadata
-from galaxy.datatypes.sniff import *
-from galaxy import eggs
-import pkg_resources
-pkg_resources.require( "bx-python" )
-from bx.seq.twobit import TWOBIT_MAGIC_NUMBER, TWOBIT_MAGIC_NUMBER_SWAP, TWOBIT_MAGIC_SIZE
-from urllib import urlencode, quote_plus
-import zipfile, gzip
-import os, subprocess, tempfile
-import struct
+
log = logging.getLogger(__name__)
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/datatypes/chrominfo.py
--- a/lib/galaxy/datatypes/chrominfo.py
+++ b/lib/galaxy/datatypes/chrominfo.py
@@ -1,7 +1,3 @@
-import data
-from galaxy import util
-from galaxy.datatypes.sniff import *
-from galaxy.web import url_for
from tabular import Tabular
from galaxy.datatypes import metadata
from galaxy.datatypes.metadata import MetadataElement
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/datatypes/coverage.py
--- a/lib/galaxy/datatypes/coverage.py
+++ b/lib/galaxy/datatypes/coverage.py
@@ -2,21 +2,14 @@
Coverage datatypes
"""
-import pkg_resources
-pkg_resources.require( "bx-python" )
-import logging, os, sys, time, tempfile, shutil
-import data
-from galaxy import util
-from galaxy.datatypes.sniff import *
-from galaxy.web import url_for
-from cgi import escape
-import urllib
-from bx.intervals.io import *
+import logging
+import math
+
+from galaxy import eggs
from galaxy.datatypes import metadata
from galaxy.datatypes.metadata import MetadataElement
from galaxy.datatypes.tabular import Tabular
-import math
log = logging.getLogger(__name__)
@@ -34,7 +27,7 @@
Assumes we have a numpy file.
"""
# Maybe if we import here people will still be able to use Galaxy when numpy kills it
- pkg_resources.require("numpy>=1.2.1")
+ eggs.require("numpy>=1.2.1")
#from numpy.lib import format
import numpy
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/datatypes/metadata.py
--- a/lib/galaxy/datatypes/metadata.py
+++ b/lib/galaxy/datatypes/metadata.py
@@ -1,17 +1,30 @@
-import sys, logging, copy, shutil, weakref, cPickle, tempfile, os
+"""
+Galaxy Metadata
+
+"""
+from galaxy import eggs
+eggs.require("simplejson")
+
+
+import copy
+import cPickle
+import logging
+import os
+import shutil
+import simplejson
+import sys
+import tempfile
+import weakref
+
from os.path import abspath
-from galaxy.util import string_as_bool, stringify_dictionary_keys, listify
+import galaxy.model
+from galaxy.util import listify, stringify_dictionary_keys, string_as_bool
from galaxy.util.odict import odict
from galaxy.web import form_builder
-import galaxy.model
from sqlalchemy.orm import object_session
-import pkg_resources
-pkg_resources.require("simplejson")
-import simplejson
-
-log = logging.getLogger( __name__ )
+log = logging.getLogger(__name__)
STATEMENTS = "__galaxy_statements__" #this is the name of the property in a Datatype class where new metadata spec element Statements are stored
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/jobs/__init__.py
--- a/lib/galaxy/jobs/__init__.py
+++ b/lib/galaxy/jobs/__init__.py
@@ -4,6 +4,7 @@
import copy
import datetime
+import galaxy
import logging
import os
import pwd
@@ -14,17 +15,15 @@
import sys
import threading
import traceback
-
-import galaxy
-from galaxy import util, model
-from galaxy.util.bunch import Bunch
+from galaxy import model, util
from galaxy.datatypes import metadata
-from galaxy.util.json import from_json_string
-from galaxy.util.expressions import ExpressionContext
+from galaxy.exceptions import ObjectInvalid
from galaxy.jobs.actions.post import ActionBox
-from galaxy.exceptions import ObjectInvalid
from galaxy.jobs.mapper import JobRunnerMapper
from galaxy.jobs.runners import BaseJobRunner
+from galaxy.util.bunch import Bunch
+from galaxy.util.expressions import ExpressionContext
+from galaxy.util.json import from_json_string
log = logging.getLogger( __name__ )
@@ -917,7 +916,8 @@
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 c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/jobs/actions/post.py
--- a/lib/galaxy/jobs/actions/post.py
+++ b/lib/galaxy/jobs/actions/post.py
@@ -1,4 +1,5 @@
-import logging, datetime
+import datetime
+import logging
from galaxy.util import send_mail
from galaxy.util.json import to_json_string
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/jobs/manager.py
--- a/lib/galaxy/jobs/manager.py
+++ b/lib/galaxy/jobs/manager.py
@@ -2,17 +2,16 @@
Top-level Galaxy job manager, moves jobs to handler(s)
"""
+import logging
import os
+import random
+import threading
import time
-import random
-import logging
-import threading
-from Queue import Queue, Empty
-from sqlalchemy.sql.expression import and_, or_
+from Queue import Empty, Queue
from galaxy import model
-from galaxy.jobs import handler, Sleeper, NoopQueue, JobWrapper
+from galaxy.jobs import handler, JobWrapper, NoopQueue, Sleeper
from galaxy.util.json import from_json_string
log = logging.getLogger( __name__ )
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/model/__init__.py
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -5,21 +5,32 @@
the relationship cardinalities are obvious (e.g. prefer Dataset to Data)
"""
-import pkg_resources
-pkg_resources.require("simplejson")
-pkg_resources.require("pexpect")
-import simplejson, os, errno, codecs, operator, socket, pexpect, logging, time
+from galaxy import eggs
+eggs.require("simplejson")
+eggs.require("pexpect")
+
+import codecs
+import errno
+import logging
+import operator
+import os
+import pexpect
+import simplejson
+import socket
+import time
+
import galaxy.datatypes
import galaxy.datatypes.registry
from galaxy.datatypes.metadata import MetadataCollection
+from galaxy.model.item_attrs import APIItem, UsesAnnotations
from galaxy.security import get_permitted_actions
-from galaxy import util
+from galaxy.util import is_multi_byte, nice_size, Params, restore_text, send_mail
from galaxy.util.bunch import Bunch
from galaxy.util.hash_util import new_secure_hash
from galaxy.web.framework.helpers import to_unicode
-from galaxy.web.form_builder import (AddressField, CheckboxField, PasswordField, SelectField, TextArea, TextField,
- WorkflowField, WorkflowMappingField, HistoryField)
-from galaxy.model.item_attrs import UsesAnnotations, APIItem
+from galaxy.web.form_builder import (AddressField, CheckboxField, HistoryField,
+ PasswordField, SelectField, TextArea, TextField, WorkflowField,
+ WorkflowMappingField)
from sqlalchemy.orm import object_session
from sqlalchemy.sql.expression import func
@@ -804,7 +815,7 @@
if self.bytes == -1:
return "unlimited"
else:
- return util.nice_size( self.bytes )
+ return nice_size( self.bytes )
class DefaultQuotaAssociation( Quota, APIItem ):
api_element_visible_keys = ( 'type', )
@@ -977,7 +988,7 @@
if not self.has_data():
return False
try:
- return util.is_multi_byte( codecs.open( self.file_name, 'r', 'utf-8' ).read( 100 ) )
+ return is_multi_byte( codecs.open( self.file_name, 'r', 'utf-8' ).read( 100 ) )
except UnicodeDecodeError:
return False
# FIXME: sqlalchemy will replace this
@@ -2275,7 +2286,7 @@
Return the list of widgets that comprise a form definition,
including field contents if any.
'''
- params = util.Params( kwd )
+ params = Params( kwd )
widgets = []
for index, field in enumerate( self.fields ):
field_type = field[ 'type' ]
@@ -2291,7 +2302,7 @@
if field_type == 'CheckboxField':
value = CheckboxField.is_checked( params.get( field_name, False ) )
else:
- value = util.restore_text( params.get( field_name, '' ) )
+ value = restore_text( params.get( field_name, '' ) )
elif contents:
try:
# This field has a saved value.
@@ -2506,7 +2517,7 @@
frm = 'galaxy-no-reply@' + host
subject = "Galaxy Sample Tracking notification: '%s' sequencing request" % self.name
try:
- util.send_mail( frm, to, subject, body, trans.app.config )
+ send_mail( frm, to, subject, body, trans.app.config )
comments = "Email notification sent to %s." % ", ".join( to ).strip().strip( ',' )
except Exception,e:
comments = "Email notification failed. (%s)" % str(e)
@@ -2548,7 +2559,7 @@
if data_transfer_protocol == self.data_transfer_protocol.SCP:
scp_configs = {}
automatic_transfer = data_transfer_obj.config.get( 'automatic_transfer', 'false' )
- scp_configs[ 'automatic_transfer' ] = util.string_as_bool( automatic_transfer )
+ scp_configs[ 'automatic_transfer' ] = galaxy.util.string_as_bool( automatic_transfer )
scp_configs[ 'host' ] = self.form_values.content.get( data_transfer_obj.config.get( 'host', '' ), '' )
scp_configs[ 'user_name' ] = self.form_values.content.get( data_transfer_obj.config.get( 'user_name', '' ), '' )
scp_configs[ 'password' ] = self.form_values.content.get( data_transfer_obj.config.get( 'password', '' ), '' )
@@ -2558,7 +2569,7 @@
if data_transfer_protocol == self.data_transfer_protocol.HTTP:
http_configs = {}
automatic_transfer = data_transfer_obj.config.get( 'automatic_transfer', 'false' )
- http_configs[ 'automatic_transfer' ] = util.string_as_bool( automatic_transfer )
+ http_configs[ 'automatic_transfer' ] = galaxy.util.string_as_bool( automatic_transfer )
self.data_transfer[ self.data_transfer_protocol.HTTP ] = http_configs
def populate_actions( self, trans, item, param_dict=None ):
return self.get_external_service_type( trans ).actions.populate( self, item, param_dict=param_dict )
diff -r c5c9a85e1bb88a609118d29d595e0136d44dff2a -r d128613ae7c9ef1387b749c7577a6631b649b048 lib/galaxy/model/custom_types.py
--- a/lib/galaxy/model/custom_types.py
+++ b/lib/galaxy/model/custom_types.py
@@ -11,9 +11,9 @@
from galaxy.util.aliaspickler import AliasPickleModule
# For monkeypatching BIGINT
-import sqlalchemy.databases.sqlite
-import sqlalchemy.databases.postgres
-import sqlalchemy.databases.mysql
+import sqlalchemy.dialects.sqlite
+import sqlalchemy.dialects.postgresql
+import sqlalchemy.dialects.mysql
import logging
log = logging.getLogger( __name__ )
@@ -39,7 +39,7 @@
Defines a JSONType for SQLAlchemy. Takes a primitive as input and
JSONifies it. This should replace PickleType throughout Galaxy.
"""
- impl = Binary
+ impl = LargeBinary
def process_bind_param( self, value, dialect ):
if value is None:
@@ -86,8 +86,6 @@
ret = None
return ret
-
-
class UUIDType(TypeDecorator):
"""
Platform-independent UUID type.
@@ -128,24 +126,24 @@
return value
-class BigInteger( Integer ):
- """
- A type for bigger ``int`` integers.
+#class BigInteger( Integer ):
+ #"""
+ #A type for bigger ``int`` integers.
- Typically generates a ``BIGINT`` in DDL, and otherwise acts like
- a normal :class:`Integer` on the Python side.
+ #Typically generates a ``BIGINT`` in DDL, and otherwise acts like
+ #a normal :class:`Integer` on the Python side.
- """
+ #"""
-class BIGINT( BigInteger ):
- """The SQL BIGINT type."""
+#class BIGINT( BigInteger ):
+ #"""The SQL BIGINT type."""
-class SLBigInteger( BigInteger ):
- def get_col_spec( self ):
- return "BIGINT"
+#class SLBigInteger( BigInteger ):
+ #def get_col_spec( self ):
+ #return "BIGINT"
-sqlalchemy.databases.sqlite.SLBigInteger = SLBigInteger
-sqlalchemy.databases.sqlite.colspecs[BigInteger] = SLBigInteger
-sqlalchemy.databases.sqlite.ischema_names['BIGINT'] = SLBigInteger
-sqlalchemy.databases.postgres.colspecs[BigInteger] = sqlalchemy.databases.postgres.PGBigInteger
-sqlalchemy.databases.mysql.colspecs[BigInteger] = sqlalchemy.databases.mysql.MSBigInteger
+#sqlalchemy.dialects.sqlite.SLBigInteger = SLBigInteger
+#sqlalchemy.dialects.sqlite.colspecs[BigInteger] = SLBigInteger
+#sqlalchemy.dialects.sqlite.ischema_names['BIGINT'] = SLBigInteger
+#sqlalchemy.dialects.postgres.colspecs[BigInteger] = sqlalchemy.dialects.postgres.PGBigInteger
+#sqlalchemy.dialects.mysql.colspecs[BigInteger] = sqlalchemy.dialects.mysql.MSBigInteger
This diff is so big that we needed to truncate the remainder.
https://bitbucket.org/galaxy/galaxy-central/commits/8f0a3c34af31/
Changeset: 8f0a3c34af31
User: dannon
Date: 2013-04-18 21:35:22
Summary: Merge with central
Affected #: 77 files
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 buildbot_setup.sh
--- a/buildbot_setup.sh
+++ b/buildbot_setup.sh
@@ -93,26 +93,49 @@
JARS="/galaxy/software/jars"
-for link in $LINKS; do
- echo "Linking $link"
- rm -f tool-data/`basename $link`
- ln -sf $link tool-data
-done
-
-if [ -d "$HYPHY" ]; then
- echo "Linking $HYPHY"
- rm -f tool-data/HYPHY
- ln -sf $HYPHY tool-data/HYPHY
+if [ ! $1 ]; then
+ type="standard"
+elif [ $1 == "-ec2" ]; then
+ type="external-ec2"
+else
+ type="unknown"
fi
-if [ -d "$JARS" ]; then
- echo "Linking $JARS"
- rm -f tool-data/shared/jars
- ln -sf $JARS tool-data/shared/jars
-fi
+case $type in
+ external*)
+ echo "Running standalone buildbot setup..."
+ for sample in tool-data/*.sample; do
+ basename=${sample%.sample}
+ if [ ! -f $basename ]; then
+ echo "Copying $sample to $basename"
+ cp "$sample" "$basename"
+ fi
+ done
+ ;;
+ *)
+ echo "Running standard buildbot setup..."
+ for link in $LINKS; do
+ echo "Linking $link"
+ rm -f tool-data/`basename $link`
+ ln -sf $link tool-data
+ done
+
+ if [ -d "$HYPHY" ]; then
+ echo "Linking $HYPHY"
+ rm -f tool-data/HYPHY
+ ln -sf $HYPHY tool-data/HYPHY
+ fi
+
+ if [ -d "$JARS" ]; then
+ echo "Linking $JARS"
+ rm -f tool-data/shared/jars
+ ln -sf $JARS tool-data/shared/jars
+ fi
+ ;;
+esac
for sample in $SAMPLES; do
- file=`echo $sample | sed -e 's/\.sample$//'`
+ file=${sample%.sample}
echo "Copying $sample to $file"
cp $sample $file
done
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 datatypes_conf.xml.sample
--- a/datatypes_conf.xml.sample
+++ b/datatypes_conf.xml.sample
@@ -159,7 +159,9 @@
<converter file="encodepeak_to_summary_tree_converter.xml" target_datatype="summary_tree"/></datatype><datatype extension="pdf" type="galaxy.datatypes.images:Pdf" mimetype="application/pdf"/>
- <datatype extension="pileup" type="galaxy.datatypes.tabular:Pileup" display_in_upload="true" />
+ <datatype extension="pileup" type="galaxy.datatypes.tabular:Pileup" display_in_upload="true">
+ <converter file="pileup_to_interval_index_converter.xml" target_datatype="interval_index"/>
+ </datatype><datatype extension="png" type="galaxy.datatypes.images:Png" mimetype="image/png"/><datatype extension="qual" type="galaxy.datatypes.qualityscore:QualityScore" /><datatype extension="qualsolexa" type="galaxy.datatypes.qualityscore:QualityScoreSolexa" display_in_upload="true"/>
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/config.py
--- a/lib/galaxy/config.py
+++ b/lib/galaxy/config.py
@@ -166,6 +166,7 @@
self.enable_whoosh_library_search = string_as_bool( kwargs.get( 'enable_whoosh_library_search', False ) )
self.whoosh_index_dir = resolve_path( kwargs.get( "whoosh_index_dir", "database/whoosh_indexes" ), self.root )
self.ftp_upload_dir = kwargs.get( 'ftp_upload_dir', None )
+ self.ftp_upload_dir_identifier = kwargs.get( 'ftp_upload_dir_identifier', 'email' ) # attribute on user - email, username, id, etc...
self.ftp_upload_site = kwargs.get( 'ftp_upload_site', None )
self.allow_library_path_paste = kwargs.get( 'allow_library_path_paste', False )
self.disable_library_comptypes = kwargs.get( 'disable_library_comptypes', '' ).lower().split( ',' )
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/binary.py
--- a/lib/galaxy/datatypes/binary.py
+++ b/lib/galaxy/datatypes/binary.py
@@ -101,6 +101,9 @@
class Bam( Binary ):
"""Class describing a BAM binary file"""
file_ext = "bam"
+ track_type = "ReadTrack"
+ data_sources = { "data": "bai", "index": [ "bigwig", "summary_tree" ] }
+
MetadataElement( name="bam_index", desc="BAM Index File", param=metadata.FileParameter, file_ext="bai", readonly=True, no_value=None, visible=False, optional=True )
def _get_samtools_version( self ):
@@ -251,9 +254,7 @@
return dataset.peek
except:
return "Binary bam alignments file (%s)" % ( data.nice_size( dataset.get_size() ) )
- def get_track_type( self ):
- return "ReadTrack", { "data": "bai", "index": [ "bigwig", "summary_tree" ] }
-
+
Binary.register_sniffable_binary_format("bam", "bam", Bam)
class H5( Binary ):
@@ -331,6 +332,9 @@
The supplemental info in the paper has the binary details:
http://bioinformatics.oxfordjournals.org/cgi/content/abstract/btq351v1
"""
+ track_type = "LineTrack"
+ data_sources = { "data_standalone": "bigwig" }
+
def __init__( self, **kwd ):
Binary.__init__( self, **kwd )
self._magic = 0x888FFC26
@@ -355,19 +359,18 @@
return dataset.peek
except:
return "Binary UCSC %s file (%s)" % ( self._name, data.nice_size( dataset.get_size() ) )
- def get_track_type( self ):
- return "LineTrack", {"data_standalone": "bigwig"}
-
+
Binary.register_sniffable_binary_format("bigwig", "bigwig", BigWig)
class BigBed(BigWig):
"""BigBed support from UCSC."""
+
+ data_sources = { "data_standalone": "bigbed" }
+
def __init__( self, **kwd ):
Binary.__init__( self, **kwd )
self._magic = 0x8789F2EB
self._name = "BigBed"
- def get_track_type( self ):
- return "LineTrack", {"data_standalone": "bigbed"}
Binary.register_sniffable_binary_format("bigbed", "bigbed", BigBed)
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/converters/pileup_to_interval_index_converter.py
--- /dev/null
+++ b/lib/galaxy/datatypes/converters/pileup_to_interval_index_converter.py
@@ -0,0 +1,39 @@
+#!/usr/bin/env python
+
+"""
+Convert from pileup file to interval index file.
+
+usage: %prog <options> in_file out_file
+"""
+
+from __future__ import division
+
+import sys, fileinput, optparse
+from galaxy import eggs
+import pkg_resources; pkg_resources.require( "bx-python" )
+from galaxy.visualization.tracks.summary import *
+from galaxy.datatypes.util.gff_util import convert_gff_coords_to_bed
+from bx.interval_index_file import Indexes
+
+def main():
+
+ # Read options, args.
+ parser = optparse.OptionParser()
+ (options, args) = parser.parse_args()
+ input_fname, output_fname = args
+
+ # Do conversion.
+ index = Indexes()
+ offset = 0
+ for line in open( input_fname, "r" ):
+ chrom, start = line.split()[ 0:2 ]
+ # Pileup format is 1-based.
+ start = int( start ) - 1
+ index.add( chrom, start, start + 1, offset )
+ offset += len( line )
+
+ index.write( open(output_fname, "w") )
+
+if __name__ == "__main__":
+ main()
+
\ No newline at end of file
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/converters/pileup_to_interval_index_converter.xml
--- /dev/null
+++ b/lib/galaxy/datatypes/converters/pileup_to_interval_index_converter.xml
@@ -0,0 +1,15 @@
+<tool id="CONVERTER_pileup_to_interval_index_0" name="Convert Pileup to Interval Index" version="1.0.0" hidden="true">
+<!-- <description>__NOT_USED_CURRENTLY_FOR_CONVERTERS__</description> -->
+ <command interpreter="python">pileup_to_interval_index_converter.py $input $output
+ </command>
+ <inputs>
+ <page>
+ <param format="pileup" name="input" type="data" label="Choose Pileup file"/>
+ </page>
+ </inputs>
+ <outputs>
+ <data format="interval_index" name="output"/>
+ </outputs>
+ <help>
+ </help>
+</tool>
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/data.py
--- a/lib/galaxy/datatypes/data.py
+++ b/lib/galaxy/datatypes/data.py
@@ -97,6 +97,12 @@
#A per datatype setting (inherited): max file size (in bytes) for setting optional metadata
_max_optional_metadata_filesize = None
+ # Trackster track type.
+ track_type = None
+
+ # Data sources.
+ data_sources = {}
+
def __init__(self, **kwd):
"""Initialize the datatype"""
object.__init__(self, **kwd)
@@ -539,21 +545,21 @@
return False
-
def merge( split_files, output_file):
"""
- TODO: Do we need to merge gzip files using gzjoin? cat seems to work,
- but might be brittle. Need to revisit this.
+ Merge files with copy.copyfileobj() will not hit the
+ max argument limitation of cat. gz and bz2 files are also working.
"""
if not split_files:
raise ValueError('Asked to merge zero files as %s' % output_file)
elif len(split_files) == 1:
- cmd = 'mv -f %s %s' % ( split_files[0], output_file )
+ shutil.copyfileobj(open(split_files[0], 'rb'), open(output_file, 'wb'))
else:
- cmd = 'cat %s > %s' % ( ' '.join(split_files), output_file )
- result = os.system(cmd)
- if result != 0:
- raise Exception('Result %s from %s' % (result, cmd))
+ fdst = open(output_file, 'wb')
+ for fsrc in split_files:
+ shutil.copyfileobj(open(fsrc, 'rb'), fdst)
+ fdst.close()
+
merge = staticmethod(merge)
def get_visualizations( self, dataset ):
@@ -561,7 +567,7 @@
Returns a list of visualizations for datatype.
"""
- if hasattr( self, 'get_track_type' ):
+ if self.track_type:
return [ 'trackster', 'circster' ]
return []
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/display_applications/application.py
--- a/lib/galaxy/datatypes/display_applications/application.py
+++ b/lib/galaxy/datatypes/display_applications/application.py
@@ -12,7 +12,7 @@
log = logging.getLogger( __name__ )
#Any basic functions that we want to provide as a basic part of parameter dict should be added to this dict
-BASE_PARAMS = { 'qp': quote_plus, 'url_for':url_for } #url_for has route memory...
+BASE_PARAMS = { 'qp': quote_plus, 'url_for':url_for }
class DisplayApplicationLink( object ):
@classmethod
@@ -40,7 +40,7 @@
self.name = None
def get_display_url( self, data, trans ):
dataset_hash, user_hash = encode_dataset_user( trans, data, None )
- return url_for( controller='/dataset',
+ return url_for( controller='dataset',
action="display_application",
dataset_id=dataset_hash,
user_id=user_hash,
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/display_applications/link_generator.py
--- a/lib/galaxy/datatypes/display_applications/link_generator.py
+++ /dev/null
@@ -1,161 +0,0 @@
-"""Classes to generate links for old-style display applications.
-
-Separating Transaction based elements of display applications from datatypes.
-"""
-
-#FIXME: The code contained within this file is for old-style display applications, but
-#this module namespace is intended to only handle the new-style display applications.
-
-import urllib
-
-# for the url_for hack
-import pkg_resources
-pkg_resources.require( "Routes" )
-import routes
-
-from galaxy import util
-from galaxy.web import url_for
-from galaxy.datatypes.interval import Interval, Gff, Wiggle, CustomTrack
-
-#TODO: Ideally, these classes would be instantiated in the trans (or some other semi-persistant fixture)
-# Currently, these are instantiated per HDA which is not the best solution
-
-#TODO: these could be extended to handle file_function and parse/contain the builds.txt files
-
-#HACK: these duplicate functionality from the individual datatype classes themselves
-
-def get_display_app_link_generator( display_app_name ):
- """Returns an instance of the proper link generator class
- based on the display_app_name or DisplayAppLinkGenerator
- if the display_app_name is unrecognized.
- """
- if display_app_name == 'ucsc':
- return UCSCDisplayAppLinkGenerator()
-
- elif display_app_name == 'gbrowse':
- return GBrowseDisplayAppLinkGenerator()
-
- return DisplayAppLinkGenerator()
-
-
-class DisplayAppLinkGenerator( object ):
- """Base class for display application link generators.
-
- This class returns an empty list of links for all datatypes.
- """
- def __init__( self ):
- self.display_app_name = ''
-
- def no_links_available( self, dataset, app, base_url, url_for=url_for ):
- """Called when no display application links are available
- for this display app name and datatype combination.
- """
- return []
-
- def _link_function_from_datatype( self, datatype ):
- """Dispatch to proper link generating function on datatype.
- """
- return self.no_links_available
-
- def generate_links( self, trans, dataset ):
- # here's the hack - which is expensive (time)
- web_url_for = routes.URLGenerator( trans.webapp.mapper, trans.environ )
-
- link_function = self._link_function_from_datatype( dataset.datatype )
- display_links = link_function( dataset, trans.app, trans.request.base, url_for=web_url_for )
-
- return display_links
-
-
-class UCSCDisplayAppLinkGenerator( DisplayAppLinkGenerator ):
- """Class for generating links to display data in the
- UCSC genome browser.
-
- This class returns links for the following datatypes and their subclasses:
- Interval, Wiggle, Gff, CustomTrack
- """
- def __init__( self ):
- self.display_app_name = 'ucsc'
-
- def _link_function_from_datatype( self, datatype ):
- """Dispatch to proper link generating function based on datatype.
- """
- if( ( isinstance( datatype, Interval ) )
- or ( isinstance( datatype, Wiggle ) )
- or ( isinstance( datatype, Gff ) )
- or ( isinstance( datatype, CustomTrack ) ) ):
- return self.ucsc_links
- else:
- return super( UCSCDisplayAppLinkGenerator, self )._link_function_from_datatype( datatype )
-
- def ucsc_links( self, dataset, app, base_url, url_for=url_for ):
- """Generate links to UCSC genome browser sites based on the dbkey
- and content of dataset.
- """
- # this is a refactor of Interval.ucsc_links, GFF.ucsc_links, Wiggle.ucsc_links, and CustomTrack.ucsc_links
- #TODO: app vars can be moved into init (and base_url as well)
- chrom, start, stop = dataset.datatype.get_estimated_display_viewport( dataset )
- if chrom is None:
- return []
- ret_val = []
- for site_name, site_url in util.get_ucsc_by_build(dataset.dbkey):
- if site_name in app.config.ucsc_display_sites:
- internal_url = url_for( controller='dataset', dataset_id=dataset.id,
- action='display_at', filename='%s_%s' % ( self.display_app_name, site_name ) )
- base_url = app.config.get( "display_at_callback", base_url )
- display_url = urllib.quote_plus( "%s%s/display_as?id=%i&display_app=%s&authz_method=display_at"
- % (base_url, url_for( controller='root' ), dataset.id, self.display_app_name) )
- redirect_url = urllib.quote_plus( "%sdb=%s&position=%s:%s-%s&hgt.customText=%%s"
- % (site_url, dataset.dbkey, chrom, start, stop ) )
-
- link = '%s?redirect_url=%s&display_url=%s' % ( internal_url, redirect_url, display_url )
- ret_val.append( ( site_name, link ) )
-
- return ret_val
-
-
-class GBrowseDisplayAppLinkGenerator( DisplayAppLinkGenerator ):
- """Class for generating links to display data in the
- GBrowse genome browser.
-
- This class returns links for the following datatypes and their subclasses:
- Gff, Wiggle
- """
- def __init__( self ):
- self.display_app_name = 'gbrowse'
-
- def _link_function_from_datatype( self, datatype ):
- """Dispatch to proper link generating function based on datatype.
- """
- if( ( isinstance( datatype, Gff ) )
- or ( isinstance( datatype, Wiggle ) ) ):
- return self.gbrowse_links
- else:
- return super( GBrowseDisplayAppLinkGenerator, self )._link_function_from_datatype( datatype )
-
- def gbrowse_links( self, dataset, app, base_url, url_for=url_for ):
- """Generate links to GBrowse genome browser sites based on the dbkey
- and content of dataset.
- """
- # when normalized for var names, Gff.gbrowse_links and Wiggle.gbrowse_links are the same
- # also: almost identical to ucsc_links except for the 'chr' stripping, sites_by_build, config key
- # could be refactored even more
- chrom, start, stop = dataset.datatype.get_estimated_display_viewport( dataset )
- if chrom is None:
- return []
- ret_val = []
- for site_name, site_url in util.get_gbrowse_sites_by_build( dataset.dbkey ):
- if site_name in app.config.gbrowse_display_sites:
- # strip chr from seqid
- if chrom.startswith( 'chr' ) and len ( chrom ) > 3:
- chrom = chrom[3:]
- internal_url = url_for( controller='dataset', dataset_id=dataset.id,
- action='display_at', filename='%s_%s' % ( self.display_app_name, site_name ) )
- redirect_url = urllib.quote_plus( "%s/?q=%s:%s..%s&eurl=%%s" % ( site_url, chrom, start, stop ) )
- base_url = app.config.get( "display_at_callback", base_url )
- display_url = urllib.quote_plus( "%s%s/display_as?id=%i&display_app=%s&authz_method=display_at"
- % ( base_url, url_for( controller='root' ), dataset.id, self.display_app_name ) )
- link = '%s?redirect_url=%s&display_url=%s' % ( internal_url, redirect_url, display_url )
- ret_val.append( ( site_name, link ) )
-
- return ret_val
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/display_applications/parameters.py
--- a/lib/galaxy/datatypes/display_applications/parameters.py
+++ b/lib/galaxy/datatypes/display_applications/parameters.py
@@ -163,7 +163,7 @@
if self.parameter.strip_https and base_url[ : 5].lower() == 'https':
base_url = "http%s" % base_url[ 5: ]
return "%s%s" % ( base_url,
- url_for( controller='/dataset',
+ url_for( controller='dataset',
action="display_application",
dataset_id=self._dataset_hash,
user_id=self._user_hash,
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/interval.py
--- a/lib/galaxy/datatypes/interval.py
+++ b/lib/galaxy/datatypes/interval.py
@@ -46,6 +46,8 @@
"""Tab delimited data containing interval information"""
file_ext = "interval"
line_class = "region"
+ track_type = "FeatureTrack"
+ data_sources = { "data": "tabix", "index": "summary_tree" }
"""Add metadata elements"""
MetadataElement( name="chromCol", default=1, desc="Chrom column", param=metadata.ColumnParameter )
@@ -242,7 +244,7 @@
# Accumulate links for valid sites
ret_val = []
for site_name, site_url in valid_sites:
- internal_url = url_for( controller='/dataset', dataset_id=dataset.id,
+ internal_url = url_for( controller='dataset', dataset_id=dataset.id,
action='display_at', filename='ucsc_' + site_name )
display_url = urllib.quote_plus( "%s%s/display_as?id=%i&display_app=%s&authz_method=display_at"
% (base_url, url_for( controller='root' ), dataset.id, type) )
@@ -328,17 +330,13 @@
def get_track_resolution( self, dataset, start, end):
return None
-
- def get_track_type( self ):
- return "FeatureTrack", {"data": "tabix", "index": "summary_tree"}
class BedGraph( Interval ):
"""Tab delimited chrom/start/end/datavalue dataset"""
file_ext = "bedgraph"
-
- def get_track_type( self ):
- return "LineTrack", { "data": "bigwig", "index": "bigwig" }
+ track_type = "LineTrack"
+ data_sources = { "data": "bigwig", "index": "bigwig" }
def as_ucsc_display_file( self, dataset, **kwd ):
"""
@@ -356,6 +354,7 @@
class Bed( Interval ):
"""Tab delimited data in BED format"""
file_ext = "bed"
+ data_sources = {"data": "tabix", "index": "summary_tree", "feature_search": "fli"}
"""Add metadata elements"""
MetadataElement( name="chromCol", default=1, desc="Chrom column", param=metadata.ColumnParameter )
@@ -510,9 +509,6 @@
else: return False
return True
except: return False
-
- def get_track_type( self ):
- return "FeatureTrack", {"data": "tabix", "index": "summary_tree", "feature_search": "fli"}
class BedStrict( Bed ):
"""Tab delimited data in strict BED format - no non-standard columns allowed"""
@@ -572,6 +568,7 @@
"""Tab delimited data in Gff format"""
file_ext = "gff"
column_names = [ 'Seqname', 'Source', 'Feature', 'Start', 'End', 'Score', 'Strand', 'Frame', 'Group' ]
+ data_sources = { "data": "interval_index", "index": "summary_tree", "feature_search": "fli" }
"""Add metadata elements"""
MetadataElement( name="columns", default=9, desc="Number of columns", readonly=True, visible=False )
@@ -783,10 +780,6 @@
return True
except:
return False
-
- def get_track_type( self ):
- return "FeatureTrack", {"data": "interval_index", "index": "summary_tree", "feature_search": "fli"}
-
class Gff3( Gff ):
"""Tab delimited data in Gff3 format"""
@@ -966,6 +959,8 @@
class Wiggle( Tabular, _RemoteCallMixin ):
"""Tab delimited data in wiggle format"""
file_ext = "wig"
+ track_type = "LineTrack"
+ data_sources = { "data": "bigwig", "index": "bigwig" }
MetadataElement( name="columns", default=3, desc="Number of columns", readonly=True, visible=False )
@@ -1146,9 +1141,6 @@
resolution = min( resolution, 100000 )
resolution = max( resolution, 1 )
return resolution
-
- def get_track_type( self ):
- return "LineTrack", { "data": "bigwig", "index": "bigwig" }
class CustomTrack ( Tabular ):
"""UCSC CustomTrack"""
@@ -1292,6 +1284,7 @@
file_ext = "encodepeak"
column_names = [ 'Chrom', 'Start', 'End', 'Name', 'Score', 'Strand', 'SignalValue', 'pValue', 'qValue', 'Peak' ]
+ data_sources = { "data": "tabix", "index": "summary_tree" }
"""Add metadata elements"""
MetadataElement( name="chromCol", default=1, desc="Chrom column", param=metadata.ColumnParameter )
@@ -1303,15 +1296,14 @@
def sniff( self, filename ):
return False
- def get_track_type( self ):
- return "FeatureTrack", {"data": "tabix", "index": "summary_tree"}
-
class ChromatinInteractions( Interval ):
'''
Chromatin interactions obtained from 3C/5C/Hi-C experiments.
'''
file_ext = "chrint"
+ track_type = "DiagonalHeatmapTrack"
+ data_sources = { "data": "tabix", "index": "summary_tree" }
column_names = [ 'Chrom1', 'Start1', 'End1', 'Chrom2', 'Start2', 'End2', 'Value' ]
@@ -1328,11 +1320,6 @@
def sniff( self, filename ):
return False
-
- def get_track_type( self ):
- return "DiagonalHeatmapTrack", {"data": "tabix", "index": "summary_tree"}
-
-
if __name__ == '__main__':
import doctest, sys
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/registry.py
--- a/lib/galaxy/datatypes/registry.py
+++ b/lib/galaxy/datatypes/registry.py
@@ -163,7 +163,7 @@
# Use default mime type as per datatype spec
mimetype = self.datatypes_by_extension[ extension ].get_mime()
self.mimetypes_by_extension[ extension ] = mimetype
- if hasattr( datatype_class, "get_track_type" ):
+ if datatype_class.track_type:
self.available_tracks.append( extension )
if display_in_upload:
self.upload_file_formats.append( extension )
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/datatypes/tabular.py
--- a/lib/galaxy/datatypes/tabular.py
+++ b/lib/galaxy/datatypes/tabular.py
@@ -358,6 +358,9 @@
class Sam( Tabular ):
file_ext = 'sam'
+ track_type = "ReadTrack"
+ data_sources = { "data": "bam", "index": "summary_tree" }
+
def __init__(self, **kwd):
"""Initialize taxonomy datatype"""
Tabular.__init__( self, **kwd )
@@ -467,13 +470,11 @@
raise Exception('Result %s from %s' % (result, cmd))
merge = staticmethod(merge)
- def get_track_type( self ):
- return "ReadTrack", {"data": "bam", "index": "summary_tree"}
-
class Pileup( Tabular ):
"""Tab delimited data in pileup (6- or 10-column) format"""
file_ext = "pileup"
line_class = "genomic coordinate"
+ data_sources = { "data": "interval_index" }
"""Add metadata elements"""
MetadataElement( name="chromCol", default=1, desc="Chrom column", param=metadata.ColumnParameter )
@@ -525,8 +526,7 @@
return True
except:
return False
-
-
+
class ElandMulti( Tabular ):
file_ext = 'elandmulti'
@@ -535,13 +535,16 @@
class Vcf( Tabular ):
""" Variant Call Format for describing SNPs and other simple genome variations. """
+ track_type = "VariantTrack"
+ data_sources = { "data": "tabix", "index": "summary_tree" }
file_ext = 'vcf'
column_names = [ 'Chrom', 'Pos', 'ID', 'Ref', 'Alt', 'Qual', 'Filter', 'Info', 'Format', 'data' ]
MetadataElement( name="columns", default=10, desc="Number of columns", readonly=True, visible=False )
MetadataElement( name="column_types", default=['str','int','str','str','str','int','str','list','str','str'], param=metadata.ColumnTypesParameter, desc="Column types", readonly=True, visible=False )
- MetadataElement( name="viz_filter_cols", desc="Score column for visualization", default=[5], param=metadata.ColumnParameter, multiple=True )
+ MetadataElement( name="viz_filter_cols", desc="Score column for visualization", default=[5], param=metadata.ColumnParameter, multiple=True, visible=False )
+ MetadataElement( name="sample_names", default=[], desc="Sample names", readonly=True, visible=False, optional=True, no_value=[] )
def sniff( self, filename ):
headers = get_headers( filename, '\n', count=1 )
@@ -551,8 +554,20 @@
"""Returns formated html of peek"""
return Tabular.make_html_table( self, dataset, column_names=self.column_names )
- def get_track_type( self ):
- return "VcfTrack", { "data": "tabix", "index": "summary_tree" }
+ def set_meta( self, dataset, **kwd ):
+ Tabular.set_meta( self, dataset, **kwd )
+ source = open( dataset.file_name )
+
+ # Skip comments.
+ line = None
+ for line in source:
+ if not line.startswith( '##' ):
+ break
+
+ if line and line.startswith( '#' ):
+ # Found header line, get sample names.
+ dataset.metadata.sample_names = line.split()[ 9: ]
+
class Eland( Tabular ):
"""Support for the export.txt.gz file used by Illumina's ELANDv2e aligner"""
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/jobs/__init__.py
--- a/lib/galaxy/jobs/__init__.py
+++ b/lib/galaxy/jobs/__init__.py
@@ -1470,6 +1470,14 @@
self.__galaxy_system_pwent = pwd.getpwuid(os.getuid())
return self.__galaxy_system_pwent
+ def get_output_destination( self, output_path ):
+ """
+ Destination for outputs marked as from_work_dir. This is the normal case,
+ just copy these files directly to the ulimate destination.
+ """
+ return output_path
+
+
class TaskWrapper(JobWrapper):
"""
Extension of JobWrapper intended for running tasks.
@@ -1691,6 +1699,15 @@
# There is no metadata setting for tasks. This is handled after the merge, at the job level.
return ""
+ def get_output_destination( self, output_path ):
+ """
+ Destination for outputs marked as from_work_dir. These must be copied with
+ the same basenme as the path for the ultimate output destination. This is
+ required in the task case so they can be merged.
+ """
+ return os.path.join( self.working_directory, os.path.basename( output_path ) )
+
+
class NoopQueue( object ):
"""
Implements the JobQueue / JobStopQueue interface but does nothing
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/jobs/runners/__init__.py
--- a/lib/galaxy/jobs/runners/__init__.py
+++ b/lib/galaxy/jobs/runners/__init__.py
@@ -226,7 +226,7 @@
# Copy from working dir to HDA.
# TODO: move instead of copy to save time?
source_file = os.path.join( os.path.abspath( job_wrapper.working_directory ), hda_tool_output.from_work_dir )
- destination = output_paths[ dataset.dataset_id ]
+ destination = job_wrapper.get_output_destination( output_paths[ dataset.dataset_id ] )
if in_directory( source_file, job_wrapper.working_directory ):
output_pairs.append( ( source_file, destination ) )
log.debug( "Copying %s to %s as directed by from_work_dir" % ( source_file, destination ) )
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/model/__init__.py
--- a/lib/galaxy/model/__init__.py
+++ b/lib/galaxy/model/__init__.py
@@ -1344,10 +1344,9 @@
with entries of type
(<datasource_type> : {<datasource_name>, <indexing_message>}).
"""
- track_type, data_sources = self.datatype.get_track_type()
data_sources_dict = {}
msg = None
- for source_type, source_list in data_sources.iteritems():
+ for source_type, source_list in self.datatype.data_sources.iteritems():
data_source = None
if source_type == "data_standalone":
# Nothing to do.
@@ -3305,16 +3304,16 @@
be installed in order for this repository to function correctly. However, those repository dependencies that are defined for this
repository with prior_installation_required set to True place them in a special category in that the required repositories must be
installed before this repository is installed. Among other things, this enables these "special" repository dependencies to include
- information that enables the successful intallation of this repository.
+ information that enables the successful intallation of this repository. This method is not used during the initial installation of
+ this repository, but only after it has been installed (metadata must be set for this repository in order for this method to be useful).
"""
required_rd_tups_that_must_be_installed = []
if self.has_repository_dependencies:
rd_tups = self.metadata[ 'repository_dependencies' ][ 'repository_dependencies' ]
for rd_tup in rd_tups:
if len( rd_tup ) == 4:
- # Metadata should have been reset on this installed tool_shed_repository, but it wasn't.
+ # For backward compatibility to the 12/20/12 Galaxy release, default prior_installation_required to False.
tool_shed, name, owner, changeset_revision = rd_tup
- # Default prior_installation_required to False.
prior_installation_required = False
elif len( rd_tup ) == 5:
tool_shed, name, owner, changeset_revision, prior_installation_required = rd_tup
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/tools/__init__.py
--- a/lib/galaxy/tools/__init__.py
+++ b/lib/galaxy/tools/__init__.py
@@ -1094,7 +1094,7 @@
self.version_string_cmd = None
version_cmd = root.find("version_command")
if version_cmd is not None:
- self.version_string_cmd = version_cmd.text
+ self.version_string_cmd = version_cmd.text.strip()
version_cmd_interpreter = version_cmd.get( "interpreter", None )
if version_cmd_interpreter:
executable = self.version_string_cmd.split()[0]
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/tools/parameters/basic.py
--- a/lib/galaxy/tools/parameters/basic.py
+++ b/lib/galaxy/tools/parameters/basic.py
@@ -475,7 +475,7 @@
if trans is None or trans.user is None:
user_ftp_dir = None
else:
- user_ftp_dir = os.path.join( trans.app.config.ftp_upload_dir, trans.user.email )
+ user_ftp_dir = trans.user_ftp_dir
return form_builder.FTPFileField( self.name, user_ftp_dir, trans.app.config.ftp_upload_site, value = value )
def from_html( self, value, trans=None, other_values={} ):
try:
@@ -623,6 +623,8 @@
def __init__( self, tool, elem, context=None ):
ToolParameter.__init__( self, tool, elem )
self.multiple = string_as_bool( elem.get( 'multiple', False ) )
+ # Multiple selects are optional by default, single selection is the inverse.
+ self.optional = string_as_bool( elem.get( 'optional', self.multiple ) )
self.display = elem.get( 'display', None )
self.separator = elem.get( 'separator', ',' )
self.legal_values = set()
@@ -712,6 +714,13 @@
rval.append( v )
return rval
else:
+ value_is_none = ( value == "None" and "None" not in legal_values )
+ if value_is_none:
+ if self.multiple:
+ if self.optional:
+ return []
+ else:
+ raise ValueError( "No option was selected but input is not optional." )
if value not in legal_values:
raise ValueError( "An invalid option was selected, please verify" )
return value
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/tools/parameters/dynamic_options.py
--- a/lib/galaxy/tools/parameters/dynamic_options.py
+++ b/lib/galaxy/tools/parameters/dynamic_options.py
@@ -129,6 +129,13 @@
rval.append( fields )
return rval
else:
+ if not self.dynamic_option.columns:
+ self.dynamic_option.columns = {
+ "name" : 0,
+ "value" : 1,
+ "selected" : 2
+ }
+ self.dynamic_option.largest_index = 2
if not isinstance( meta_value, list ):
meta_value = [meta_value]
for value in meta_value:
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/tools/parameters/grouping.py
--- a/lib/galaxy/tools/parameters/grouping.py
+++ b/lib/galaxy/tools/parameters/grouping.py
@@ -270,7 +270,7 @@
if file_bunch.path and ftp_files is not None:
warnings.append( "All FTP uploaded file selections were ignored." )
elif ftp_files is not None and trans.user is not None: # look for files uploaded via FTP
- user_ftp_dir = os.path.join( trans.app.config.ftp_upload_dir, trans.user.email )
+ user_ftp_dir = trans.user_ftp_dir
for ( dirpath, dirnames, filenames ) in os.walk( user_ftp_dir ):
for filename in filenames:
for ftp_filename in ftp_files:
@@ -318,7 +318,7 @@
ftp_files = []
# TODO: warning to the user (could happen if session has become invalid)
else:
- user_ftp_dir = os.path.join( trans.app.config.ftp_upload_dir, trans.user.email )
+ user_ftp_dir = trans.user_ftp_dir
for ( dirpath, dirnames, filenames ) in os.walk( user_ftp_dir ):
for filename in filenames:
path = relpath( os.path.join( dirpath, filename ), user_ftp_dir )
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/visualization/data_providers/genome.py
--- a/lib/galaxy/visualization/data_providers/genome.py
+++ b/lib/galaxy/visualization/data_providers/genome.py
@@ -2,7 +2,7 @@
Data providers for genome visualizations.
"""
-import os, sys, operator
+import os, sys, re
from math import ceil, log
import pkg_resources
pkg_resources.require( "bx-python" )
@@ -601,12 +601,22 @@
"""
Abstract class that processes VCF data from native format to payload format.
- Payload format: TODO
+ Payload format: An array of entries for each locus in the file. Each array
+ has the following entries:
+ 1. GUID (unused)
+ 2. location (0-based)
+ 3. reference base(s)
+ 4. alternative base(s)
+ 5. quality score
+ 6. whether variant passed filter
+ 7. sample genotypes -- a single string with samples separated by commas; empty string
+ denotes the reference genotype
+ 8-end: allele counts for each alternative
"""
col_name_data_attr_mapping = { 'Qual' : { 'index': 6 , 'name' : 'Qual' } }
- dataset_type = 'bai'
+ dataset_type = 'variant'
def process_data( self, iterator, start_val=0, max_vals=None, **kwargs ):
"""
@@ -621,7 +631,7 @@
message - error/informative message
"""
- rval = []
+ data = []
message = None
def get_mapping( ref, alt ):
@@ -651,6 +661,7 @@
return ref_in_alt_index, alt[ ref_in_alt_index + 1: ], [ [ cig_ops.find( "I" ), alt_len - ref_len ] ]
# Pack data.
+ genotype_re = re.compile( '/|\|' )
for count, line in enumerate( iterator ):
if count < start_val:
continue
@@ -658,37 +669,66 @@
message = self.error_max_vals % ( max_vals, "features" )
break
+ # Split line and aggregate data.
feature = line.split()
- start = int( feature[1] ) - 1
- ref = feature[3]
- alts = feature[4]
+ pos, c_id, ref, alt, qual, c_filter, info = feature[ 1:8 ]
+ format = feature[ 8 ]
+ samples_data = feature [ 9: ]
+ # VCF is 1-based.
+ pos = int( pos ) - 1
+
+ # FIXME: OK to skip?
+ if alt == '.':
+ count -= 1
+ continue
- # HACK? alts == '.' --> monomorphism.
- if alts == '.':
- alts = ref
+ # Count number of samples matching each allele.
+ allele_counts = [ 0 for i in range ( alt.count( ',' ) + 1 ) ]
- # Pack variants.
- for alt in alts.split(","):
- offset, new_seq, cigar = get_mapping( ref, alt )
- start += offset
- end = start + len( new_seq )
+ # Process and pack sample genotype.
+ sample_gts = []
+ alleles_seen = {}
+ has_alleles = False
- # Pack line.
- payload = [
- hash( line ),
- start,
- end,
- # ID:
- feature[2],
- cigar,
- # TODO? VCF does not have strand, so default to positive.
- "+",
- new_seq,
- None if feature[5] == '.' else float( feature[5] )
- ]
- rval.append(payload)
+ for i, sample in enumerate( samples_data ):
+ # Parse and count alleles.
+ genotype = sample.split( ':' )[ 0 ]
+ has_alleles = False
+ alleles_seen.clear()
+ for allele in genotype_re.split( genotype ):
+ try:
+ # This may throw a ValueError if allele is missing.
+ allele = int( allele )
- return { 'data': rval, 'message': message }
+ # Only count allele if it hasn't been seen yet.
+ if allele != 0 and allele not in alleles_seen:
+ allele_counts[ allele - 1 ] += 1
+ alleles_seen[ allele ] = True
+ has_alleles = True
+ except ValueError:
+ pass
+
+ # If no alleles, use empty string as proxy.
+ if not has_alleles:
+ genotype = ''
+
+ sample_gts.append( genotype )
+
+ # Add locus data.
+ locus_data = [
+ -1,
+ pos,
+ c_id,
+ ref,
+ alt,
+ qual,
+ c_filter,
+ ','.join( sample_gts )
+ ]
+ locus_data.extend( allele_counts )
+ data.append( locus_data )
+
+ return { 'data': data, 'message': message }
def write_data_to_file( self, regions, filename ):
out = open( filename, "w" )
@@ -707,7 +747,8 @@
"""
Provides data from a VCF file indexed via tabix.
"""
- pass
+
+ dataset_type = 'variant'
class RawVcfDataProvider( VcfDataProvider ):
"""
@@ -718,29 +759,45 @@
"""
def get_iterator( self, chrom, start, end, **kwargs ):
- # Read first line in order to match chrom naming format.
- line = source.readline()
- dataset_chrom = line.split()[0]
- if not _chrom_naming_matches( chrom, dataset_chrom ):
- chrom = _convert_between_ucsc_and_ensemble_naming( chrom )
- # Undo read.
- source.seek( 0 )
+ source = open( self.original_dataset.file_name )
+
+ # Skip comments.
+ pos = 0
+ line = None
+ for line in source:
+ if not line.startswith("#"):
+ break
+ else:
+ pos = source.tell()
+
+ # If last line is a comment, there are no data lines.
+ if line.startswith( "#" ):
+ return []
+
+ # Match chrom naming format.
+ if line:
+ dataset_chrom = line.split()[0]
+ if not _chrom_naming_matches( chrom, dataset_chrom ):
+ chrom = _convert_between_ucsc_and_ensemble_naming( chrom )
+
+ def line_in_region( vcf_line, chrom, start, end ):
+ """ Returns true if line is in region. """
+ variant_chrom, variant_start = vcf_line.split()[ 0:2 ]
+ # VCF format is 1-based.
+ variant_start = int( variant_start ) - 1
+ return variant_chrom == chrom and variant_start >= start and variant_start <= end
def line_filter_iter():
- for line in open( self.original_dataset.file_name ):
- if line.startswith("#"):
- continue
- variant = line.split()
- variant_chrom, variant_start, id, ref, alts = variant[ 0:5 ]
- variant_start = int( variant_start )
- longest_alt = -1
- for alt in alts:
- if len( alt ) > longest_alt:
- longest_alt = len( alt )
- variant_end = variant_start + abs( len( ref ) - longest_alt )
- if variant_chrom != chrom or variant_start > end or variant_end < start:
- continue
+ """ Yields lines in source that are in region chrom:start-end """
+ # Yield data line read above.
+ if line_in_region( line, chrom, start, end ):
yield line
+
+ # Search for and yield other data lines.
+ for data_line in source:
+ if line_in_region( data_line, chrom, start, end ):
+ print chrom, start, end, ">>>", data_line,
+ yield data_line
return line_filter_iter()
@@ -1012,34 +1069,44 @@
# If there are results and reference data, transform read sequence and cigar.
if len( results ) != 0 and ref_seq:
+ def process_read( read, start_field, cigar_field, seq_field ):
+ '''
+ Process a read using the designated fields.
+ '''
+ read_seq, read_cigar = get_ref_based_read_seq_and_cigar( read[ seq_field ].upper(),
+ read[ start_field ],
+ ref_seq,
+ start,
+ read[ cigar_field ] )
+ read[ seq_field ] = read_seq
+ read[ cigar_field ] = read_cigar
+
def process_se_read( read ):
'''
Process single-end read.
'''
- read_seq, read_cigar = get_ref_based_read_seq_and_cigar( read[ 6 ].upper(), read[ 1 ],
- ref_seq, start, read[ 4 ] )
- read[ 6 ] = read_seq
- read[ 4 ] = read_cigar
-
+ process_read( read, 1, 4, 6)
+
def process_pe_read( read ):
'''
Process paired-end read.
'''
- process_se_read( read[ 4 ] )
- process_se_read( read[ 5 ] )
+ if len( read[4] ) > 2:
+ process_read( read[4], 0, 2, 4 )
+ if len( read[5] ) > 2:
+ process_read( read[5], 0, 2, 4 )
# Uppercase for easy comparison.
ref_seq = ref_seq.upper()
- # Choose correct function for processing reads.
- process_fn = process_se_read
- if isinstance( results[ 0 ][ 5 ], list ):
- process_fn = process_pe_read
-
# Process reads.
for read in results:
- process_fn( read )
-
+ # Use correct function for processing reads.
+ if isinstance( read[ 5 ], list ):
+ process_pe_read( read )
+ else:
+ process_se_read( read )
+
max_low, max_high = get_bounds( results, 1, 2 )
return { 'data': results, 'message': message, 'max_low': max_low, 'max_high': max_high }
@@ -1050,14 +1117,16 @@
def __init__( self, converted_dataset=None, original_dataset=None, dependencies=None ):
""" Create SamDataProvider. """
+ super( SamDataProvider, self ).__init__( converted_dataset=converted_dataset,
+ original_dataset=original_dataset,
+ dependencies=dependencies )
- # HACK: to use BamDataProvider, original dataset must be BAM and
+ # To use BamDataProvider, original dataset must be BAM and
# converted dataset must be BAI. Use BAI from BAM metadata.
if converted_dataset:
+ self.original_dataset = converted_dataset
self.converted_dataset = converted_dataset.metadata.bam_index
- self.original_dataset = converted_dataset
- self.dependencies = dependencies
-
+
class BBIDataProvider( GenomeDataProvider ):
"""
BBI data provider for the Galaxy track browser.
@@ -1207,7 +1276,7 @@
class IntervalIndexDataProvider( FilterableMixin, GenomeDataProvider ):
"""
- Interval index files used only for GFF files.
+ Interval index files used for GFF, Pileup files.
"""
col_name_data_attr_mapping = { 4 : { 'index': 4 , 'name' : 'Score' } }
@@ -1217,20 +1286,26 @@
source = open( self.original_dataset.file_name )
index = Indexes( self.converted_dataset.file_name )
out = open( filename, 'w' )
-
+
for region in regions:
# Write data from region.
chrom = region.chrom
start = region.start
end = region.end
- for start, end, offset in index.find(chrom, start, end):
+ for start, end, offset in index.find( chrom, start, end ):
source.seek( offset )
-
- reader = GFFReaderWrapper( source, fix_strand=True )
- feature = reader.next()
- for interval in feature.intervals:
- out.write( '\t'.join( interval.fields ) + '\n' )
-
+
+ # HACK: write differently depending on original dataset format.
+ if self.original_dataset.ext not in [ 'gff', 'gff3', 'gtf' ]:
+ line = source.readline()
+ out.write( line )
+ else:
+ reader = GFFReaderWrapper( source, fix_strand=True )
+ feature = reader.next()
+ for interval in feature.intervals:
+ out.write( '\t'.join( interval.fields ) + '\n' )
+
+ source.close()
out.close()
def get_iterator( self, chrom, start, end, **kwargs ):
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/visualization/data_providers/registry.py
--- a/lib/galaxy/visualization/data_providers/registry.py
+++ b/lib/galaxy/visualization/data_providers/registry.py
@@ -83,12 +83,12 @@
elif original_dataset:
# No name, so look up a provider name from datatype's information.
- # Dataset must have get_track_type function to get data.
- if not hasattr( original_dataset.datatype, 'get_track_type'):
+ # Dataset must have data sources to get data.
+ if not original_dataset.datatype.data_sources:
return None
# Get data provider mapping and data provider.
- _ , data_provider_mapping = original_dataset.datatype.get_track_type()
+ data_provider_mapping = original_dataset.datatype.data_sources
if 'data_standalone' in data_provider_mapping:
data_provider = self.get_data_provider( trans,
name=data_provider_mapping[ 'data_standalone' ],
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/visualization/genome/visual_analytics.py
--- a/lib/galaxy/visualization/genome/visual_analytics.py
+++ b/lib/galaxy/visualization/genome/visual_analytics.py
@@ -76,5 +76,5 @@
# If tool has parameters that can be interactively modified, return tool.
if len( tool_params ) != 0:
- return { 'name' : tool.name, 'params' : tool_params }
+ return { 'id': tool.id, 'name' : tool.name, 'params' : tool_params }
return None
\ No newline at end of file
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/web/base/controller.py
--- a/lib/galaxy/web/base/controller.py
+++ b/lib/galaxy/web/base/controller.py
@@ -32,8 +32,6 @@
from galaxy.datatypes.display_applications import util as da_util
from galaxy.datatypes.metadata import FileParameter
-from galaxy.datatypes.display_applications.link_generator import get_display_app_link_generator
-
log = logging.getLogger( __name__ )
# States for passing messages
@@ -392,28 +390,18 @@
})
def get_display_apps( self, trans, hda ):
- #TODO: make more straightforward (somehow)
display_apps = []
+ for display_app in hda.get_display_applications( trans ).itervalues():
- def get_display_app_url( display_app_link, hda, trans ):
- web_url_for = routes.URLGenerator( trans.webapp.mapper, trans.environ )
- dataset_hash, user_hash = da_util.encode_dataset_user( trans, hda, None )
- return web_url_for( controller='dataset',
- action="display_application",
- dataset_id=dataset_hash,
- user_id=user_hash,
- app_name=urllib.quote_plus( display_app_link.display_application.id ),
- link_name=urllib.quote_plus( display_app_link.id ) )
-
- for display_app in hda.get_display_applications( trans ).itervalues():
app_links = []
- for display_app_link in display_app.links.itervalues():
+ for link_app in display_app.links.itervalues():
app_links.append({
- 'target' : display_app_link.url.get( 'target_frame', '_blank' ),
- 'href' : get_display_app_url( display_app_link, hda, trans ),
- 'text' : gettext( display_app_link.name )
+ 'target': link_app.url.get( 'target_frame', '_blank' ),
+ 'href' : link_app.get_display_url( hda, trans ),
+ 'text' : gettext( link_app.name )
})
- display_apps.append( dict( label=display_app.name, links=app_links ) )
+ if app_links:
+ display_apps.append( dict( label=display_app.name, links=app_links ) )
return display_apps
@@ -421,19 +409,23 @@
display_apps = []
if not trans.app.config.enable_old_display_applications:
return display_apps
- for display_app_name in hda.datatype.get_display_types():
- link_generator = get_display_app_link_generator( display_app_name )
- display_links = link_generator.generate_links( trans, hda )
+
+ for display_app in hda.datatype.get_display_types():
+ target_frame, display_links = hda.datatype.get_display_links( hda,
+ display_app, trans.app, trans.request.base )
- app_links = []
- for display_name, display_link in display_links:
- app_links.append({
- 'target' : '_blank',
- 'href' : display_link,
- 'text' : display_name
- })
- if app_links:
- display_apps.append( dict( label=hda.datatype.get_display_label( display_app_name ), links=app_links ) )
+ if len( display_links ) > 0:
+ display_label = hda.datatype.get_display_label( display_app )
+
+ app_links = []
+ for display_name, display_link in display_links:
+ app_links.append({
+ 'target': target_frame,
+ 'href' : display_link,
+ 'text' : gettext( display_name )
+ })
+ if app_links:
+ display_apps.append( dict( label=display_label, links=app_links ) )
return display_apps
@@ -590,15 +582,13 @@
except KeyError:
prefs = {}
- track_type, _ = dataset.datatype.get_track_type()
track_data_provider = trans.app.data_provider_registry.get_data_provider( trans,
original_dataset=dataset,
source='data' )
return {
- "track_type": track_type,
+ "track_type": dataset.datatype.track_type,
+ "dataset": trans.security.encode_dict_ids( dataset.get_api_value() ),
"name": track_dict['name'],
- "hda_ldda": track_dict.get("hda_ldda", "hda"),
- "dataset_id": trans.security.encode_id( dataset.id ),
"prefs": prefs,
"mode": track_dict.get( 'mode', 'Auto' ),
"filters": track_dict.get( 'filters', { 'filters' : track_data_provider.get_filters() } ),
@@ -666,10 +656,8 @@
Returns track configuration dict for a dataset.
"""
# Get data provider.
- track_type, _ = dataset.datatype.get_track_type()
track_data_provider = trans.app.data_provider_registry.get_data_provider( trans, original_dataset=dataset )
-
if isinstance( dataset, trans.app.model.HistoryDatasetAssociation ):
hda_ldda = "hda"
elif isinstance( dataset, trans.app.model.LibraryDatasetDatasetAssociation ):
@@ -677,10 +665,9 @@
# Get track definition.
return {
- "track_type": track_type,
+ "track_type": dataset.datatype.track_type,
"name": dataset.name,
- "hda_ldda": hda_ldda,
- "dataset_id": trans.security.encode_id( dataset.id ),
+ "dataset": trans.security.encode_dict_ids( dataset.get_api_value() ),
"prefs": {},
"filters": { 'filters' : track_data_provider.get_filters() },
"tool": get_tool_def( trans, dataset ),
@@ -967,7 +954,7 @@
return state
- def get_history_dict( self, trans, history ):
+ def get_history_dict( self, trans, history, hda_dictionaries=None ):
"""Returns history data in the form of a dictionary.
"""
history_dict = history.get_api_value( view='element', value_mapper={ 'id':trans.security.encode_id })
@@ -979,8 +966,7 @@
if not history_dict[ 'annotation' ]:
history_dict[ 'annotation' ] = ''
- #TODO: allow passing as arg
- hda_summaries = self.get_hda_summary_dicts( trans, history )
+ hda_summaries = hda_dictionaries if hda_dictionaries else self.get_hda_summary_dicts( trans, history )
#TODO remove the following in v2
( state_counts, state_ids ) = self._get_hda_state_summaries( trans, hda_summaries )
history_dict[ 'state_details' ] = state_counts
diff -r d128613ae7c9ef1387b749c7577a6631b649b048 -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 lib/galaxy/web/framework/__init__.py
--- a/lib/galaxy/web/framework/__init__.py
+++ b/lib/galaxy/web/framework/__init__.py
@@ -112,34 +112,25 @@
def expose_api_anonymous( func, to_json=True ):
"""
- Expose this function via the API but don't require an API key.
+ Expose this function via the API but don't require a set user.
"""
- return expose_api( func, to_json=to_json, key_required=False )
+ return expose_api( func, to_json=to_json, user_required=False )
-def expose_api( func, to_json=True, key_required=True ):
+def expose_api( func, to_json=True, user_required=True ):
+ """
+ Expose this function via the API.
+ """
@wraps(func)
def decorator( self, trans, *args, **kwargs ):
def error( environ, start_response ):
start_response( error_status, [('Content-type', 'text/plain')] )
return error_message
error_status = '403 Forbidden'
- #If no key supplied, we use the existing session which may be an anonymous user.
- if key_required and not trans.user:
- try:
- if 'key' not in kwargs:
- raise NoResultFound( 'No key provided' )
- provided_key = trans.sa_session.query( trans.app.model.APIKeys ).filter( trans.app.model.APIKeys.table.c.key == kwargs['key'] ).one()
- except NoResultFound:
- error_message = 'Provided API key is not valid.'
- return error
- if provided_key.user.deleted:
- error_message = 'User account is deactivated, please contact an administrator.'
- return error
- newest_key = provided_key.user.api_keys[0]
- if newest_key.key != provided_key.key:
- error_message = 'Provided API key has expired.'
- return error
- trans.set_user( provided_key.user )
+ if trans.error_message:
+ return trans.error_message
+ if user_required and trans.user is None:
+ error_message = "API Authentication Required for this request"
+ return error
if trans.request.body:
def extract_payload_from_request(trans, func, kwargs):
content_type = trans.request.headers['content-type']
@@ -238,6 +229,7 @@
def form( *args, **kwargs ):
return FormBuilder( *args, **kwargs )
+
class WebApplication( base.WebApplication ):
def __init__( self, galaxy_app, session_cookie='galaxysession', name=None ):
@@ -326,6 +318,7 @@
controller_name = getattr( T, "controller_name", name )
self.add_api_controller( controller_name, T( app ) )
+
class GalaxyWebTransaction( base.DefaultWebTransaction ):
"""
Encapsulates web transaction specific state for the Galaxy application
@@ -346,13 +339,26 @@
# Flag indicating whether this is an API call and the API key user is an administrator
self.api_inherit_admin = False
self.__user = None
- # Always have a valid galaxy session
- self._ensure_valid_session( session_cookie )
- # Prevent deleted users from accessing Galaxy
- if self.app.config.use_remote_user and self.galaxy_session.user.deleted:
- self.response.send_redirect( url_for( '/static/user_disabled.html' ) )
- if self.app.config.require_login:
- self._ensure_logged_in_user( environ, session_cookie )
+ self.galaxy_session = None
+ self.error_message = None
+ if self.environ.get('is_api_request', False):
+ # With API requests, if there's a key, use it and associate the
+ # user with the transaction.
+ # If not, check for an active session but do not create one.
+ # If an error message is set here, it's sent back using
+ # trans.show_error in the response -- in expose_api.
+ self.error_message = self._authenticate_api( session_cookie )
+ else:
+ #This is a web request, get or create session.
+ self._ensure_valid_session( session_cookie )
+ if self.galaxy_session:
+ # When we've authenticated by session, we have to check the
+ # following.
+ # Prevent deleted users from accessing Galaxy
+ if self.app.config.use_remote_user and self.galaxy_session.user.deleted:
+ self.response.send_redirect( url_for( '/static/user_disabled.html' ) )
+ if self.app.config.require_login:
+ self._ensure_logged_in_user( environ, session_cookie )
def setup_i18n( self ):
locales = []
@@ -382,16 +388,17 @@
def get_user( self ):
"""Return the current user if logged in or None."""
- if self.__user:
+ if self.galaxy_session:
+ return self.galaxy_session.user
+ else:
return self.__user
- else:
- return self.galaxy_session.user
def set_user( self, user ):
"""Set the current user."""
- self.galaxy_session.user = user
- self.sa_session.add( self.galaxy_session )
- self.sa_session.flush()
+ if self.galaxy_session:
+ self.galaxy_session.user = user
+ self.sa_session.add( self.galaxy_session )
+ self.sa_session.flush()
self.__user = user
user = property( get_user, set_user )
@@ -473,6 +480,33 @@
except CookieError, e:
log.warning( "Error setting httponly attribute in cookie '%s': %s" % ( name, e ) )
+ def _authenticate_api( self, session_cookie ):
+ """
+ Authenticate for the API via key or session (if available).
+ """
+ api_key = self.request.params.get('key', None)
+ secure_id = self.get_cookie( name=session_cookie )
+ if self.environ.get('is_api_request', False) and api_key:
+ # Sessionless API transaction, we just need to associate a user.
+ try:
+ provided_key = self.sa_session.query( self.app.model.APIKeys ).filter( self.app.model.APIKeys.table.c.key == api_key ).one()
+ except NoResultFound:
+ return 'Provided API key is not valid.'
+ if provided_key.user.deleted:
+ return 'User account is deactivated, please contact an administrator.'
+ newest_key = provided_key.user.api_keys[0]
+ if newest_key.key != provided_key.key:
+ return 'Provided API key has expired.'
+ self.set_user( provided_key.user )
+ elif secure_id:
+ # API authentication via active session
+ # Associate user using existing session
+ self._ensure_valid_session( session_cookie )
+ else:
+ # Anonymous API interaction -- anything but @expose_api_anonymous will fail past here.
+ self.user = None
+ self.galaxy_session = None
+
def _ensure_valid_session( self, session_cookie, create=True):
"""
Ensure that a valid Galaxy session exists and is available as
@@ -505,8 +539,11 @@
.filter( and_( self.app.model.GalaxySession.table.c.session_key==session_key,
self.app.model.GalaxySession.table.c.is_valid==True ) ) \
.first()
- # If remote user is in use it can invalidate the session, so we need to to check some things now.
+ # If remote user is in use it can invalidate the session and in some
+ # cases won't have a cookie set above, so we need to to check some
+ # things now.
if self.app.config.use_remote_user:
+ #If this is an api request, and they've passed a key, we let this go.
assert "HTTP_REMOTE_USER" in self.environ, \
"use_remote_user is set but no HTTP_REMOTE_USER variable"
remote_user_email = self.environ[ 'HTTP_REMOTE_USER' ]
@@ -605,6 +642,7 @@
pass
if self.request.path not in allowed_paths:
self.response.send_redirect( url_for( controller='root', action='index' ) )
+
def __create_new_session( self, prev_galaxy_session=None, user_for_new_session=None ):
"""
Create a new GalaxySession for this request, possibly with a connection
@@ -627,6 +665,7 @@
# The new session should be associated with the user
galaxy_session.user = user_for_new_session
return galaxy_session
+
def get_or_create_remote_user( self, remote_user_email ):
"""
Create a remote user with the email remote_user_email and return it
@@ -671,11 +710,14 @@
self.app.security_agent.user_set_default_permissions( user )
#self.log_event( "Automatically created account '%s'", user.email )
return user
+
def __update_session_cookie( self, name='galaxysession' ):
"""
Update the session cookie to match the current session.
"""
- self.set_cookie( self.security.encode_guid( self.galaxy_session.session_key ), name=name, path=self.app.config.cookie_path )
+ self.set_cookie( self.security.encode_guid(self.galaxy_session.session_key ),
+ name=name, path=self.app.config.cookie_path )
+
def handle_user_login( self, user ):
"""
Login a new user (possibly newly created)
@@ -701,9 +743,9 @@
except:
users_last_session = None
last_accessed = False
- if prev_galaxy_session.current_history and \
- not prev_galaxy_session.current_history.deleted and \
- prev_galaxy_session.current_history.datasets:
+ if (prev_galaxy_session.current_history and not
+ prev_galaxy_session.current_history.deleted and
+ prev_galaxy_session.current_history.datasets):
if prev_galaxy_session.current_history.user is None or prev_galaxy_session.current_history.user == user:
# If the previous galaxy session had a history, associate it with the new
# session, but only if it didn't belong to a different user.
@@ -714,10 +756,9 @@
user.total_disk_usage += hda.quota_amount( user )
elif self.galaxy_session.current_history:
history = self.galaxy_session.current_history
- if not history and \
- users_last_session and \
- users_last_session.current_history and \
- not users_last_session.current_history.deleted:
+ if (not history and users_last_session and
+ users_last_session.current_history and not
+ users_last_session.current_history.deleted):
history = users_last_session.current_history
elif not history:
history = self.get_history( create=True )
@@ -736,6 +777,8 @@
self.sa_session.flush()
# This method is not called from the Galaxy reports, so the cookie will always be galaxysession
self.__update_session_cookie( name=cookie_name )
+
+
def handle_user_logout( self, logout_all=False ):
"""
Logout the current user:
@@ -760,31 +803,38 @@
self.__update_session_cookie( name='galaxysession' )
elif self.webapp.name == 'tool_shed':
self.__update_session_cookie( name='galaxycommunitysession' )
+
def get_galaxy_session( self ):
"""
Return the current galaxy session
"""
return self.galaxy_session
+
def get_history( self, create=False ):
"""
Load the current history, creating a new one only if there is not
- current history and we're told to create"
+ current history and we're told to create.
+ Transactions will not always have an active history (API requests), so
+ None is a valid response.
"""
- history = self.galaxy_session.current_history
- if not history:
- if util.string_as_bool( create ):
- history = self.new_history()
- else:
- # Perhaps a bot is running a tool without having logged in to get a history
- log.debug( "This request returned None from get_history(): %s" % self.request.browser_url )
- return None
+ history = None
+ if self.galaxy_session:
+ history = self.galaxy_session.current_history
+ if not history and util.string_as_bool( create ):
+ history = self.new_history()
+ else:
+ # Perhaps a bot is running a tool without having logged in to get a history
+ log.debug( "This request returned None from get_history(): %s" % self.request.browser_url )
return history
+
def set_history( self, history ):
if history and not history.deleted:
self.galaxy_session.current_history = history
self.sa_session.add( self.galaxy_session )
self.sa_session.flush()
+
history = property( get_history, set_history )
+
def new_history( self, name=None ):
"""
Create a new history and associate it with the current session and
@@ -809,6 +859,7 @@
self.sa_session.add_all( ( self.galaxy_session, history ) )
self.sa_session.flush()
return history
+
def get_current_user_roles( self ):
user = self.get_user()
if user:
@@ -816,27 +867,34 @@
else:
roles = []
return roles
+
def user_is_admin( self ):
if self.api_inherit_admin:
return True
admin_users = [ x.strip() for x in self.app.config.get( "admin_users", "" ).split( "," ) ]
return self.user and admin_users and self.user.email in admin_users
+
def user_can_do_run_as( self ):
run_as_users = self.app.config.get( "api_allow_run_as", "" ).split( "," )
return self.user and run_as_users and self.user.email in run_as_users
+
def get_toolbox(self):
"""Returns the application toolbox"""
return self.app.toolbox
+
@base.lazy_property
def template_context( self ):
return dict()
+
@property
def model( self ):
return self.app.model
+
def make_form_data( self, name, **kwargs ):
rval = self.template_context[name] = FormData()
rval.values.update( kwargs )
return rval
+
def set_message( self, message, type=None ):
"""
Convenience method for setting the 'message' and 'message_type'
@@ -845,12 +903,14 @@
self.template_context['message'] = message
if type:
self.template_context['status'] = type
+
def get_message( self ):
"""
Convenience method for getting the 'message' element of the template
context.
"""
return self.template_context['message']
+
def show_message( self, message, type='info', refresh_frames=[], cont=None, use_panels=False, active_view="" ):
"""
Convenience method for displaying a simple page with a single message.
@@ -862,21 +922,25 @@
refreshed when the message is displayed
"""
return self.fill_template( "message.mako", status=type, message=message, refresh_frames=refresh_frames, cont=cont, use_panels=use_panels, active_view=active_view )
+
def show_error_message( self, message, refresh_frames=[], use_panels=False, active_view="" ):
"""
Convenience method for displaying an error message. See `show_message`.
"""
return self.show_message( message, 'error', refresh_frames, use_panels=use_panels, active_view=active_view )
+
def show_ok_message( self, message, refresh_frames=[], use_panels=False, active_view="" ):
"""
Convenience method for displaying an ok message. See `show_message`.
"""
return self.show_message( message, 'done', refresh_frames, use_panels=use_panels, active_view=active_view )
+
def show_warn_message( self, message, refresh_frames=[], use_panels=False, active_view="" ):
"""
Convenience method for displaying an warn message. See `show_message`.
"""
return self.show_message( message, 'warning', refresh_frames, use_panels=use_panels, active_view=active_view )
+
def show_form( self, form, header=None, template="form.mako", use_panels=False, active_view="" ):
"""
Convenience method for displaying a simple page with a single HTML
@@ -884,6 +948,7 @@
"""
return self.fill_template( template, form=form, header=header, use_panels=( form.use_panels or use_panels ),
active_view=active_view )
+
def fill_template(self, filename, **kwargs):
"""
Fill in a template, putting any keyword arguments on the context.
@@ -897,6 +962,7 @@
template = Template( file=os.path.join(self.app.config.template_path, filename),
searchList=[kwargs, self.template_context, dict(caller=self, t=self, h=helpers, util=util, request=self.request, response=self.response, app=self.app)] )
return str( template )
+
def fill_template_mako( self, filename, **kwargs ):
template = self.webapp.mako_template_lookup.get_template( filename )
template.output_encoding = 'utf-8'
@@ -904,6 +970,7 @@
data.update( self.template_context )
data.update( kwargs )
return template.render( **data )
+
def stream_template_mako( self, filename, **kwargs ):
template = self.webapp.mako_template_lookup.get_template( filename )
template.output_encoding = 'utf-8'
@@ -921,6 +988,7 @@
template.render_context( context )
return []
return render
+
def fill_template_string(self, template_string, context=None, **kwargs):
"""
Fill in a template, putting any keyword arguments on the context.
@@ -960,6 +1028,11 @@
def ncbi_builds( self ):
return util.dlnames['ncbi']
+ @property
+ def user_ftp_dir( self ):
+ identifier = self.app.config.ftp_upload_dir_identifier
+ return os.path.join( self.app.config.ftp_upload_dir, getattr(self.user, identifier) )
+
def db_dataset_for( self, dbkey ):
"""
Returns the db_file dataset associated/needed by `dataset`, or `None`.
@@ -983,6 +1056,7 @@
return True
return False
+
class FormBuilder( object ):
"""
Simple class describing an HTML form
@@ -994,17 +1068,22 @@
self.submit_text = submit_text
self.inputs = []
self.use_panels = use_panels
+
def add_input( self, type, name, label, value=None, error=None, help=None, use_label=True ):
self.inputs.append( FormInput( type, label, name, value, error, help, use_label ) )
return self
+
def add_text( self, name, label, value=None, error=None, help=None ):
return self.add_input( 'text', label, name, value, error, help )
+
def add_password( self, name, label, value=None, error=None, help=None ):
return self.add_input( 'password', label, name, value, error, help )
+
def add_select( self, name, label, value=None, options=[], error=None, help=None, use_label=True ):
self.inputs.append( SelectInput( name, label, value=value, options=options, error=error, help=help, use_label=use_label ) )
return self
+
class FormInput( object ):
"""
Simple class describing a form input element
@@ -1018,12 +1097,14 @@
self.help = help
self.use_label = use_label
+
class SelectInput( FormInput ):
""" A select form input. """
def __init__( self, name, label, value=None, options=[], error=None, help=None, use_label=True ):
FormInput.__init__( self, "select", name, label, value=value, error=error, help=help, use_label=use_label )
self.options = options
+
class FormData( object ):
"""
Class for passing data about a form to a template, very rudimentary, could
@@ -1033,6 +1114,7 @@
self.values = Bunch()
self.errors = Bunch()
+
class Bunch( dict ):
"""
Bunch based on a dict
@@ -1042,3 +1124,4 @@
return self[key]
def __setattr__( self, key, value ):
self[key] = value
+
This diff is so big that we needed to truncate the remainder.
https://bitbucket.org/galaxy/galaxy-central/commits/90e18fe3eb82/
Changeset: 90e18fe3eb82
User: dannon
Date: 2013-04-18 23:57:52
Summary: Merge
Affected #: 4 files
diff -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 -r 90e18fe3eb822d7b9380b554cd7464f083f0e931 static/scripts/packed/viz/trackster/painters.js
--- a/static/scripts/packed/viz/trackster/painters.js
+++ b/static/scripts/packed/viz/trackster/painters.js
@@ -1,1 +1,1 @@
-define(["libs/underscore"],function(_){var extend=_.extend;var BEFORE=1001,CONTAINS=1002,OVERLAP_START=1003,OVERLAP_END=1004,CONTAINED_BY=1005,AFTER=1006;var compute_overlap=function(first_region,second_region){var first_start=first_region[0],first_end=first_region[1],second_start=second_region[0],second_end=second_region[1],overlap;if(first_start<second_start){if(first_end<=second_start){overlap=BEFORE}else{if(first_end<=second_end){overlap=OVERLAP_START}else{overlap=CONTAINS}}}else{if(first_start>second_end){overlap=AFTER}else{if(first_end<=second_end){overlap=CONTAINED_BY}else{overlap=OVERLAP_END}}}return overlap};var is_overlap=function(first_region,second_region){var overlap=compute_overlap(first_region,second_region);return(overlap!==BEFORE&&overlap!==AFTER)};var dashedLine=function(ctx,x1,y1,x2,y2,dashLen){if(dashLen===undefined){dashLen=4}var dX=x2-x1;var dY=y2-y1;var dashes=Math.floor(Math.sqrt(dX*dX+dY*dY)/dashLen);var dashX=dX/dashes;var dashY=dY/dashes;var q;for(q=0;q<dashes;q++,x1+=dashX,y1+=dashY){if(q%2!==0){continue}ctx.fillRect(x1,y1,dashLen,1)}};var drawDownwardEquilateralTriangle=function(ctx,down_vertex_x,down_vertex_y,side_len){var x1=down_vertex_x-side_len/2,x2=down_vertex_x+side_len/2,y=down_vertex_y-Math.sqrt(side_len*3/2);ctx.beginPath();ctx.moveTo(x1,y);ctx.lineTo(x2,y);ctx.lineTo(down_vertex_x,down_vertex_y);ctx.lineTo(x1,y);ctx.strokeStyle=this.fillStyle;ctx.fill();ctx.stroke();ctx.closePath()};var Scaler=function(default_val){this.default_val=(default_val?default_val:1)};Scaler.prototype.gen_val=function(input){return this.default_val};var Painter=function(data,view_start,view_end,prefs,mode){this.data=data;this.view_start=view_start;this.view_end=view_end;this.prefs=extend({},this.default_prefs,prefs);this.mode=mode};Painter.prototype.default_prefs={};Painter.prototype.draw=function(ctx,width,height,w_scale){};var SummaryTreePainter=function(data,view_start,view_end,prefs,mode){Painter.call(this,data,view_start,view_end,prefs,mode)};SummaryTreePainter.prototype.default_prefs={show_counts:false};SummaryTreePainter.prototype.draw=function(ctx,width,height,w_scale){var view_start=this.view_start,points=this.data.data,max=(this.prefs.histogram_max?this.prefs.histogram_max:this.data.max),base_y=height,delta_x_px=Math.ceil(this.data.delta*w_scale);ctx.save();for(var i=0,len=points.length;i<len;i++){var x=Math.floor((points[i][0]-view_start)*w_scale);var y=points[i][1];if(!y){continue}var y_px=y/max*height;if(y!==0&&y_px<1){y_px=1}ctx.fillStyle=this.prefs.block_color;ctx.fillRect(x,base_y-y_px,delta_x_px,y_px);var text_padding_req_x=4;if(this.prefs.show_counts&&(ctx.measureText(y).width+text_padding_req_x)<delta_x_px){ctx.fillStyle=this.prefs.label_color;ctx.textAlign="center";ctx.fillText(y,x+(delta_x_px/2),10)}}ctx.restore()};var LinePainter=function(data,view_start,view_end,prefs,mode){Painter.call(this,data,view_start,view_end,prefs,mode);var i,len;if(this.prefs.min_value===undefined){var min_value=Infinity;for(i=0,len=this.data.length;i<len;i++){min_value=Math.min(min_value,this.data[i][1])}this.prefs.min_value=min_value}if(this.prefs.max_value===undefined){var max_value=-Infinity;for(i=0,len=this.data.length;i<len;i++){max_value=Math.max(max_value,this.data[i][1])}this.prefs.max_value=max_value}};LinePainter.prototype.default_prefs={min_value:undefined,max_value:undefined,mode:"Histogram",color:"#000",overflow_color:"#F66"};LinePainter.prototype.draw=function(ctx,width,height,w_scale){var in_path=false,min_value=this.prefs.min_value,max_value=this.prefs.max_value,vertical_range=max_value-min_value,height_px=height,view_start=this.view_start,mode=this.mode,data=this.data;ctx.save();var y_zero=Math.round(height+min_value/vertical_range*height);if(mode!=="Intensity"){ctx.fillStyle="#aaa";ctx.fillRect(0,y_zero,width,1)}ctx.beginPath();var x_scaled,y,delta_x_px;if(data.length>1){delta_x_px=Math.ceil((data[1][0]-data[0][0])*w_scale)}else{delta_x_px=10}var pref_color=parseInt(this.prefs.color.slice(1),16),pref_r=(pref_color&16711680)>>16,pref_g=(pref_color&65280)>>8,pref_b=pref_color&255;for(var i=0,len=data.length;i<len;i++){ctx.fillStyle=ctx.strokeStyle=this.prefs.color;x_scaled=Math.round((data[i][0]-view_start-0.5)*w_scale);y=data[i][1];var top_overflow=false,bot_overflow=false;if(y===null){if(in_path&&mode==="Filled"){ctx.lineTo(x_scaled,height_px)}in_path=false;continue}if(y<min_value){bot_overflow=true;y=min_value}else{if(y>max_value){top_overflow=true;y=max_value}}if(mode==="Histogram"){y=Math.round(y/vertical_range*height_px);ctx.fillRect(x_scaled,y_zero,delta_x_px,-y)}else{if(mode==="Intensity"){var saturation=(y-min_value)/vertical_range,new_r=Math.round(pref_r+(255-pref_r)*(1-saturation)),new_g=Math.round(pref_g+(255-pref_g)*(1-saturation)),new_b=Math.round(pref_b+(255-pref_b)*(1-saturation));ctx.fillStyle="rgb("+new_r+","+new_g+","+new_b+")";ctx.fillRect(x_scaled,0,delta_x_px,height_px)}else{y=Math.round(height_px-(y-min_value)/vertical_range*height_px);if(in_path){ctx.lineTo(x_scaled,y)}else{in_path=true;if(mode==="Filled"){ctx.moveTo(x_scaled,height_px);ctx.lineTo(x_scaled,y)}else{ctx.moveTo(x_scaled,y)}}}}ctx.fillStyle=this.prefs.overflow_color;if(top_overflow||bot_overflow){var overflow_x;if(mode==="Histogram"||mode==="Intensity"){overflow_x=delta_x_px}else{x_scaled-=2;overflow_x=4}if(top_overflow){ctx.fillRect(x_scaled,0,overflow_x,3)}if(bot_overflow){ctx.fillRect(x_scaled,height_px-3,overflow_x,3)}}ctx.fillStyle=this.prefs.color}if(mode==="Filled"){if(in_path){ctx.lineTo(x_scaled,y_zero);ctx.lineTo(0,y_zero)}ctx.fill()}else{ctx.stroke()}ctx.restore()};var FeaturePositionMapper=function(slot_height){this.feature_positions={};this.slot_height=slot_height;this.translation=0;this.y_translation=0};FeaturePositionMapper.prototype.map_feature_data=function(feature_data,slot,x_start,x_end){if(!this.feature_positions[slot]){this.feature_positions[slot]=[]}this.feature_positions[slot].push({data:feature_data,x_start:x_start,x_end:x_end})};FeaturePositionMapper.prototype.get_feature_data=function(x,y){var slot=Math.floor((y-this.y_translation)/this.slot_height),feature_dict;if(!this.feature_positions[slot]){return null}x+=this.translation;for(var i=0;i<this.feature_positions[slot].length;i++){feature_dict=this.feature_positions[slot][i];if(x>=feature_dict.x_start&&x<=feature_dict.x_end){return feature_dict.data}}};var FeaturePainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler){Painter.call(this,data,view_start,view_end,prefs,mode);this.alpha_scaler=(alpha_scaler?alpha_scaler:new Scaler());this.height_scaler=(height_scaler?height_scaler:new Scaler())};FeaturePainter.prototype.default_prefs={block_color:"#FFF",connector_color:"#FFF"};extend(FeaturePainter.prototype,{get_required_height:function(rows_required,width){var required_height=this.get_row_height(),y_scale=required_height,mode=this.mode;if(mode==="no_detail"||mode==="Squish"||mode==="Pack"){required_height=rows_required*y_scale}return required_height+this.get_top_padding(width)+this.get_bottom_padding(width)},get_top_padding:function(width){return 0},get_bottom_padding:function(width){return Math.max(Math.round(this.get_row_height()/2),5)},draw:function(ctx,width,height,w_scale,slots){var data=this.data,view_start=this.view_start,view_end=this.view_end;ctx.save();ctx.fillStyle=this.prefs.block_color;ctx.textAlign="right";var y_scale=this.get_row_height(),feature_mapper=new FeaturePositionMapper(y_scale),x_draw_coords;for(var i=0,len=data.length;i<len;i++){var feature=data[i],feature_uid=feature[0],feature_start=feature[1],feature_end=feature[2],slot=(slots&&slots[feature_uid]!==undefined?slots[feature_uid]:null);if((feature_start<view_end&&feature_end>view_start)&&(this.mode==="Dense"||slot!==null)){x_draw_coords=this.draw_element(ctx,this.mode,feature,slot,view_start,view_end,w_scale,y_scale,width);feature_mapper.map_feature_data(feature,slot,x_draw_coords[0],x_draw_coords[1])}}ctx.restore();feature_mapper.y_translation=this.get_top_padding(width);return feature_mapper},draw_element:function(ctx,mode,feature,slot,tile_low,tile_high,w_scale,y_scale,width){console.log("WARNING: Unimplemented function.");return[0,0]}});var DENSE_TRACK_HEIGHT=10,NO_DETAIL_TRACK_HEIGHT=3,SQUISH_TRACK_HEIGHT=5,PACK_TRACK_HEIGHT=10,NO_DETAIL_FEATURE_HEIGHT=1,DENSE_FEATURE_HEIGHT=9,SQUISH_FEATURE_HEIGHT=3,PACK_FEATURE_HEIGHT=9,LABEL_SPACING=2,CONNECTOR_COLOR="#ccc";var LinkedFeaturePainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler){FeaturePainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler);this.draw_background_connector=true;this.draw_individual_connectors=false};extend(LinkedFeaturePainter.prototype,FeaturePainter.prototype,{get_row_height:function(){var mode=this.mode,height;if(mode==="Dense"){height=DENSE_TRACK_HEIGHT}else{if(mode==="no_detail"){height=NO_DETAIL_TRACK_HEIGHT}else{if(mode==="Squish"){height=SQUISH_TRACK_HEIGHT}else{height=PACK_TRACK_HEIGHT}}}return height},draw_element:function(ctx,mode,feature,slot,tile_low,tile_high,w_scale,y_scale,width){var feature_uid=feature[0],feature_start=feature[1],feature_end=feature[2],feature_name=feature[3],feature_strand=feature[4],f_start=Math.floor(Math.max(0,(feature_start-tile_low-0.5)*w_scale)),f_end=Math.ceil(Math.min(width,Math.max(0,(feature_end-tile_low-0.5)*w_scale))),draw_start=f_start,draw_end=f_end,y_center=(mode==="Dense"?0:(0+slot))*y_scale+this.get_top_padding(width),thickness,y_start,thick_start=null,thick_end=null,block_color=(!feature_strand||feature_strand==="+"||feature_strand==="."?this.prefs.block_color:this.prefs.reverse_strand_color);label_color=this.prefs.label_color;ctx.globalAlpha=this.alpha_scaler.gen_val(feature);if(mode==="Dense"){slot=1}if(mode==="no_detail"){ctx.fillStyle=block_color;ctx.fillRect(f_start,y_center+5,f_end-f_start,NO_DETAIL_FEATURE_HEIGHT)}else{var feature_ts=feature[5],feature_te=feature[6],feature_blocks=feature[7],full_height=true;if(feature_ts&&feature_te){thick_start=Math.floor(Math.max(0,(feature_ts-tile_low)*w_scale));thick_end=Math.ceil(Math.min(width,Math.max(0,(feature_te-tile_low)*w_scale)))}var thin_height,thick_height;if(mode==="Squish"){thin_height=1;thick_height=SQUISH_FEATURE_HEIGHT;full_height=false}else{if(mode==="Dense"){thin_height=5;thick_height=DENSE_FEATURE_HEIGHT}else{thin_height=5;thick_height=PACK_FEATURE_HEIGHT}}if(!feature_blocks){ctx.fillStyle=block_color;ctx.fillRect(f_start,y_center+1,f_end-f_start,thick_height);if(feature_strand&&full_height){if(feature_strand==="+"){ctx.fillStyle=ctx.canvas.manager.get_pattern("right_strand_inv")}else{if(feature_strand==="-"){ctx.fillStyle=ctx.canvas.manager.get_pattern("left_strand_inv")}}ctx.fillRect(f_start,y_center+1,f_end-f_start,thick_height)}}else{var cur_y_center,cur_height;if(mode==="Squish"||mode==="Dense"){cur_y_center=y_center+Math.floor(SQUISH_FEATURE_HEIGHT/2)+1;cur_height=1}else{if(feature_strand){cur_y_center=y_center;cur_height=thick_height}else{cur_y_center+=(SQUISH_FEATURE_HEIGHT/2)+1;cur_height=1}}if(this.draw_background_connector){if(mode==="Squish"||mode==="Dense"){ctx.fillStyle=CONNECTOR_COLOR}else{if(feature_strand){if(feature_strand==="+"){ctx.fillStyle=ctx.canvas.manager.get_pattern("right_strand")}else{if(feature_strand==="-"){ctx.fillStyle=ctx.canvas.manager.get_pattern("left_strand")}}}else{ctx.fillStyle=CONNECTOR_COLOR}}ctx.fillRect(f_start,cur_y_center,f_end-f_start,cur_height)}var start_and_height;for(var k=0,k_len=feature_blocks.length;k<k_len;k++){var block=feature_blocks[k],block_start=Math.floor(Math.max(0,(block[0]-tile_low-0.5)*w_scale)),block_end=Math.ceil(Math.min(width,Math.max((block[1]-tile_low-0.5)*w_scale))),last_block_start,last_block_end;if(block_start>block_end){continue}ctx.fillStyle=block_color;ctx.fillRect(block_start,y_center+(thick_height-thin_height)/2+1,block_end-block_start,thin_height);if(thick_start!==undefined&&feature_te>feature_ts&&!(block_start>thick_end||block_end<thick_start)){var block_thick_start=Math.max(block_start,thick_start),block_thick_end=Math.min(block_end,thick_end);ctx.fillRect(block_thick_start,y_center+1,block_thick_end-block_thick_start,thick_height);if(feature_blocks.length===1&&mode==="Pack"){if(feature_strand==="+"){ctx.fillStyle=ctx.canvas.manager.get_pattern("right_strand_inv")}else{if(feature_strand==="-"){ctx.fillStyle=ctx.canvas.manager.get_pattern("left_strand_inv")}}if(block_thick_start+14<block_thick_end){block_thick_start+=2;block_thick_end-=2}ctx.fillRect(block_thick_start,y_center+1,block_thick_end-block_thick_start,thick_height)}}if(this.draw_individual_connectors&&last_block_start){this.draw_connector(ctx,last_block_start,last_block_end,block_start,block_end,y_center)}last_block_start=block_start;last_block_end=block_end}if(mode==="Pack"){ctx.globalAlpha=1;ctx.fillStyle="white";var hscale_factor=this.height_scaler.gen_val(feature),new_height=Math.ceil(thick_height*hscale_factor),ws_height=Math.round((thick_height-new_height)/2);if(hscale_factor!==1){ctx.fillRect(f_start,cur_y_center+1,f_end-f_start,ws_height);ctx.fillRect(f_start,cur_y_center+thick_height-ws_height+1,f_end-f_start,ws_height)}}}ctx.globalAlpha=1;if(feature_name&&mode==="Pack"&&feature_start>tile_low){ctx.fillStyle=label_color;if(tile_low===0&&f_start-ctx.measureText(feature_name).width<0){ctx.textAlign="left";ctx.fillText(feature_name,f_end+LABEL_SPACING,y_center+8);draw_end+=ctx.measureText(feature_name).width+LABEL_SPACING}else{ctx.textAlign="right";ctx.fillText(feature_name,f_start-LABEL_SPACING,y_center+8);draw_start-=ctx.measureText(feature_name).width+LABEL_SPACING}}}ctx.globalAlpha=1;return[draw_start,draw_end]}});var ReadPainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler,ref_seq,base_color_fn){FeaturePainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler);this.ref_seq=(ref_seq?ref_seq.data:null);this.base_color_fn=base_color_fn};extend(ReadPainter.prototype,FeaturePainter.prototype,{get_row_height:function(){var height,mode=this.mode;if(mode==="Dense"){height=DENSE_TRACK_HEIGHT}else{if(mode==="Squish"){height=SQUISH_TRACK_HEIGHT}else{height=PACK_TRACK_HEIGHT;if(this.prefs.show_insertions){height*=2}}}return height},_parse_cigar:function(cigar_str){var cigar_ops="MIDNSHP=X";var blocks=[[0,0]],cur_block=blocks[0],base_pos=0,parsed_cigar=_.map(cigar_str.match(/[0-9]+[MIDNSHP=X]/g),function(op){var op_len=parseInt(op.slice(0,-1),10),op_char=op.slice(-1);if(op_char==="N"){if(cur_block[1]!==0){cur_block=[base_pos+op_len,base_pos+op_len];blocks.push(cur_block)}}else{if("ISHP".indexOf(op_char)===-1){cur_block[1]+=op_len;base_pos+=op_len}}return[cigar_ops.indexOf(op_char),op_len]});return{blocks:blocks,cigar:parsed_cigar}},draw_read:function(ctx,mode,w_scale,y_center,tile_low,tile_high,feature_start,cigar,strand,read_seq){ctx.textAlign="center";var tile_region=[tile_low,tile_high],base_offset=0,seq_offset=0,gap=Math.round(w_scale/2),char_width_px=ctx.canvas.manager.char_width_px,block_color=(strand==="+"?this.prefs.block_color:this.prefs.reverse_strand_color),pack_mode=(mode==="Pack");var draw_last=[];if(!cigar){cigar=[[0,read_seq.length]]}for(var cig_id=0,len=cigar.length;cig_id<len;cig_id++){var cig=cigar[cig_id],cig_op="MIDNSHP=X"[cig[0]],cig_len=cig[1];var seq_start=feature_start+base_offset,s_start=Math.floor(Math.max(-0.5*w_scale,(seq_start-tile_low-0.5)*w_scale)),s_end=Math.floor(Math.max(0,(seq_start+cig_len-tile_low-0.5)*w_scale));if(s_start===s_end){s_end+=1}switch(cig_op){case"H":break;case"S":seq_offset+=cig_len;break;case"M":case"=":case"X":if(is_overlap([seq_start,seq_start+cig_len],tile_region)){ctx.fillStyle=block_color;ctx.fillRect(s_start,y_center+(pack_mode?1:4),s_end-s_start,(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT));var seq=read_seq.slice(seq_offset,seq_offset+cig_len),ref_char,read_char;for(var c=0,str_len=seq.length;c<str_len;c++){if(seq_start+c>=tile_low&&seq_start+c<=tile_high){ref_char=(this.ref_seq?this.ref_seq[seq_start-tile_low+c]:null);read_char=seq[c];if((ref_char&&(!this.prefs.show_differences||(read_char.toLowerCase!=="n"&&(ref_char.toLowerCase()!==read_char.toLowerCase()))))||(!ref_char&&!this.prefs.show_differences)){var c_start=Math.floor(Math.max(0,(seq_start+c-tile_low)*w_scale));ctx.fillStyle=this.base_color_fn(seq[c]);if(pack_mode&&w_scale>char_width_px){ctx.fillText(seq[c],c_start,y_center+9)}else{if(w_scale>0.05){ctx.fillRect(c_start-gap,y_center+(pack_mode?1:4),Math.max(1,Math.round(w_scale)),(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT))}}}}}}seq_offset+=cig_len;base_offset+=cig_len;break;case"N":ctx.fillStyle=CONNECTOR_COLOR;ctx.fillRect(s_start,y_center+5,s_end-s_start,1);base_offset+=cig_len;break;case"D":ctx.fillStyle="black";ctx.fillRect(s_start,y_center+4,s_end-s_start,3);base_offset+=cig_len;break;case"P":break;case"I":var insert_x_coord=s_start-gap;if(is_overlap([seq_start,seq_start+cig_len],tile_region)){var seq=read_seq.slice(seq_offset,seq_offset+cig_len);if(this.prefs.show_insertions){var x_center=s_start-(s_end-s_start)/2;if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){ctx.fillStyle="yellow";ctx.fillRect(x_center-gap,y_center-9,s_end-s_start,9);draw_last[draw_last.length]={type:"triangle",data:[insert_x_coord,y_center+4,5]};ctx.fillStyle=CONNECTOR_COLOR;switch(compute_overlap([seq_start,seq_start+cig_len],tile_region)){case (OVERLAP_START):seq=seq.slice(tile_low-seq_start);break;case (OVERLAP_END):seq=seq.slice(0,seq_start-tile_high);break;case (CONTAINED_BY):break;case (CONTAINS):seq=seq.slice(tile_low-seq_start,seq_start-tile_high);break}for(var c=0,str_len=seq.length;c<str_len;c++){var c_start=Math.floor(Math.max(0,(seq_start+c-tile_low)*w_scale));ctx.fillText(seq[c],c_start-(s_end-s_start)/2,y_center)}}else{ctx.fillStyle="yellow";ctx.fillRect(x_center,y_center+(this.mode!=="Dense"?2:5),s_end-s_start,(mode!=="Dense"?SQUISH_FEATURE_HEIGHT:DENSE_FEATURE_HEIGHT))}}else{if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){draw_last.push({type:"text",data:[seq.length,insert_x_coord,y_center+9]})}else{}}}seq_offset+=cig_len;break}}ctx.fillStyle="yellow";var item,type,data;for(var i=0;i<draw_last.length;i++){item=draw_last[i];type=item.type;data=item.data;if(type==="text"){ctx.save();ctx.font="bold "+ctx.font;ctx.fillText(data[0],data[1],data[2]);ctx.restore()}else{if(type==="triangle"){drawDownwardEquilateralTriangle(ctx,data[0],data[1],data[2])}}}},draw_element:function(ctx,mode,feature,slot,tile_low,tile_high,w_scale,y_scale,width){var feature_uid=feature[0],feature_start=feature[1],feature_end=feature[2],feature_name=feature[3],f_start=Math.floor(Math.max(-0.5*w_scale,(feature_start-tile_low-0.5)*w_scale)),f_end=Math.ceil(Math.min(width,Math.max(0,(feature_end-tile_low-0.5)*w_scale))),y_center=(mode==="Dense"?0:(0+slot))*y_scale,label_color=this.prefs.label_color;if(feature[5] instanceof Array){var b1_start=Math.floor(Math.max(0,(feature[4][0]-tile_low)*w_scale)),b1_end=Math.ceil(Math.min(width,Math.max(0,(feature[4][1]-tile_low)*w_scale))),b2_start=Math.floor(Math.max(0,(feature[5][0]-tile_low)*w_scale)),b2_end=Math.ceil(Math.min(width,Math.max(0,(feature[5][1]-tile_low)*w_scale))),connector=true;if(feature[4][1]>=tile_low&&feature[4][0]<=tile_high&&feature[4][2]){this.draw_read(ctx,mode,w_scale,y_center,tile_low,tile_high,feature[4][0],feature[4][2],feature[4][3],feature[4][4])}else{connector=false}if(feature[5][1]>=tile_low&&feature[5][0]<=tile_high&&feature[5][2]){this.draw_read(ctx,mode,w_scale,y_center,tile_low,tile_high,feature[5][0],feature[5][2],feature[5][3],feature[5][4])}else{connector=false}if(connector&&b2_start>b1_end){ctx.fillStyle=CONNECTOR_COLOR;dashedLine(ctx,b1_end,y_center+5,b2_start,y_center+5)}}else{this.draw_read(ctx,mode,w_scale,y_center,tile_low,tile_high,feature_start,feature[4],feature[5],feature[6])}if(mode==="Pack"&&feature_start>=tile_low&&feature_name!=="."){ctx.fillStyle=this.prefs.label_color;if(tile_low===0&&f_start-ctx.measureText(feature_name).width<0){ctx.textAlign="left";ctx.fillText(feature_name,f_end+LABEL_SPACING,y_center+8)}else{ctx.textAlign="right";ctx.fillText(feature_name,f_start-LABEL_SPACING,y_center+8)}}return[0,0]}});var RefBasedReadPainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler,ref_seq,base_color_fn){ReadPainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler,ref_seq,base_color_fn)};extend(RefBasedReadPainter.prototype,ReadPainter.prototype,FeaturePainter,{draw_read:function(ctx,mode,w_scale,y_center,tile_low,tile_high,feature_start,cigar,strand,read_seq){ctx.textAlign="center";var tile_region=[tile_low,tile_high],base_offset=0,seq_offset=0,gap=Math.round(w_scale/2),char_width_px=ctx.canvas.manager.char_width_px,block_color=(strand==="+"?this.prefs.block_color:this.prefs.reverse_strand_color),pack_mode=(mode==="Pack"),drawing_blocks=[];var draw_last=[];var t=this._parse_cigar(cigar);cigar=t.cigar;drawing_blocks=t.blocks;for(var i=0;i<drawing_blocks.length;i++){var block=drawing_blocks[i];if(is_overlap([feature_start+block[0],feature_start+block[1]],tile_region)){var s_start=Math.floor(Math.max(-0.5*w_scale,(feature_start+block[0]-tile_low-0.5)*w_scale)),s_end=Math.floor(Math.max(0,(feature_start+block[1]-tile_low-0.5)*w_scale));if(s_start===s_end){s_end+=1}ctx.fillStyle=block_color;ctx.fillRect(s_start,y_center+(pack_mode?1:4),s_end-s_start,(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT))}}for(var cig_id=0,len=cigar.length;cig_id<len;cig_id++){var cig=cigar[cig_id],cig_op="MIDNSHP=X"[cig[0]],cig_len=cig[1];var seq_start=feature_start+base_offset,s_start=Math.floor(Math.max(0,-0.5*w_scale,(seq_start-tile_low-0.5)*w_scale)),s_end=Math.floor(Math.max(0,(seq_start+cig_len-tile_low-0.5)*w_scale));if(s_start===s_end){s_end+=1}switch(cig_op){case"H":case"S":case"P":break;case"M":base_offset+=cig_len;break;case"=":case"X":if(is_overlap([seq_start,seq_start+cig_len],tile_region)){var cur_seq="";if(cig_op==="X"){cur_seq=read_seq.slice(seq_offset,seq_offset+cig_len)}else{if(this.ref_seq){cur_seq=this.ref_seq.slice(Math.max(0,seq_start-tile_low),Math.min(seq_start-tile_low+cig_len,tile_high-tile_low))}}var start_pos=Math.max(seq_start,tile_low);for(var c=0;c<cur_seq.length;c++){if(cur_seq&&!this.prefs.show_differences||cig_op==="X"){var c_start=Math.floor(Math.max(0,(start_pos+c-tile_low)*w_scale));ctx.fillStyle=this.base_color_fn(cur_seq[c]);if(pack_mode&&w_scale>char_width_px){ctx.fillText(cur_seq[c],c_start,y_center+9)}else{if(w_scale>0.05){ctx.fillRect(c_start-gap,y_center+(pack_mode?1:4),Math.max(1,Math.round(w_scale)),(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT))}}}}}if(cig_op==="X"){seq_offset+=cig_len}base_offset+=cig_len;break;case"N":ctx.fillStyle=CONNECTOR_COLOR;ctx.fillRect(s_start,y_center+5,s_end-s_start,1);base_offset+=cig_len;break;case"D":ctx.fillStyle="black";ctx.fillRect(s_start,y_center+4,s_end-s_start,3);base_offset+=cig_len;break;case"I":var insert_x_coord=s_start-gap;if(is_overlap([seq_start,seq_start+cig_len],tile_region)){var seq=read_seq.slice(seq_offset,seq_offset+cig_len);if(this.prefs.show_insertions){var x_center=s_start-(s_end-s_start)/2;if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){ctx.fillStyle="yellow";ctx.fillRect(x_center-gap,y_center-9,s_end-s_start,9);draw_last[draw_last.length]={type:"triangle",data:[insert_x_coord,y_center+4,5]};ctx.fillStyle=CONNECTOR_COLOR;switch(compute_overlap([seq_start,seq_start+cig_len],tile_region)){case (OVERLAP_START):seq=seq.slice(tile_low-seq_start);break;case (OVERLAP_END):seq=seq.slice(0,seq_start-tile_high);break;case (CONTAINED_BY):break;case (CONTAINS):seq=seq.slice(tile_low-seq_start,seq_start-tile_high);break}for(var c=0,str_len=seq.length;c<str_len;c++){var c_start=Math.floor(Math.max(0,(seq_start+c-tile_low)*w_scale));ctx.fillText(seq[c],c_start-(s_end-s_start)/2,y_center)}}else{ctx.fillStyle="yellow";ctx.fillRect(x_center,y_center+(this.mode!=="Dense"?2:5),s_end-s_start,(mode!=="Dense"?SQUISH_FEATURE_HEIGHT:DENSE_FEATURE_HEIGHT))}}else{if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){draw_last.push({type:"text",data:[seq.length,insert_x_coord,y_center+9]})}else{}}}seq_offset+=cig_len;break}}ctx.fillStyle="yellow";var item,type,data;for(var i=0;i<draw_last.length;i++){item=draw_last[i];type=item.type;data=item.data;if(type==="text"){ctx.save();ctx.font="bold "+ctx.font;ctx.fillText(data[0],data[1],data[2]);ctx.restore()}else{if(type==="triangle"){drawDownwardEquilateralTriangle(ctx,data[0],data[1],data[2])}}}}});var ArcLinkedFeaturePainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler){LinkedFeaturePainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler);this.longest_feature_length=this.calculate_longest_feature_length();this.draw_background_connector=false;this.draw_individual_connectors=true};extend(ArcLinkedFeaturePainter.prototype,FeaturePainter.prototype,LinkedFeaturePainter.prototype,{calculate_longest_feature_length:function(){var longest_feature_length=0;for(var i=0,len=this.data.length;i<len;i++){var feature=this.data[i],feature_start=feature[1],feature_end=feature[2];longest_feature_length=Math.max(longest_feature_length,feature_end-feature_start)}return longest_feature_length},get_top_padding:function(width){var view_range=this.view_end-this.view_start,w_scale=width/view_range;return Math.min(128,Math.ceil((this.longest_feature_length/2)*w_scale))},draw_connector:function(ctx,block1_start,block1_end,block2_start,block2_end,y_center){var x_center=(block1_end+block2_start)/2,radius=block2_start-x_center;var angle1=Math.PI,angle2=0;if(radius>0){ctx.beginPath();ctx.arc(x_center,y_center,block2_start-x_center,Math.PI,0);ctx.stroke()}}});var Color=function(rgb,a){if(Array.isArray(rgb)){this.rgb=rgb}else{if(rgb.length==6){this.rgb=rgb.match(/.{2}/g).map(function(c){return parseInt(c,16)})}else{if(rgb.length==7){this.rgb=rgb.substring(1,7).match(/.{2}/g).map(function(c){return parseInt(c,16)})}else{this.rgb=rgb.split("").map(function(c){return parseInt(c+c,16)})}}}this.alpha=typeof(a)==="number"?a:1};Color.prototype={eval:function(){return this},toCSS:function(){if(this.alpha<1){return"rgba("+this.rgb.map(function(c){return Math.round(c)}).concat(this.alpha).join(", ")+")"}else{return"#"+this.rgb.map(function(i){i=Math.round(i);i=(i>255?255:(i<0?0:i)).toString(16);return i.length===1?"0"+i:i}).join("")}},toHSL:function(){var r=this.rgb[0]/255,g=this.rgb[1]/255,b=this.rgb[2]/255,a=this.alpha;var max=Math.max(r,g,b),min=Math.min(r,g,b);var h,s,l=(max+min)/2,d=max-min;if(max===min){h=s=0}else{s=l>0.5?d/(2-max-min):d/(max+min);switch(max){case r:h=(g-b)/d+(g<b?6:0);break;case g:h=(b-r)/d+2;break;case b:h=(r-g)/d+4;break}h/=6}return{h:h*360,s:s,l:l,a:a}},toARGB:function(){var argb=[Math.round(this.alpha*255)].concat(this.rgb);return"#"+argb.map(function(i){i=Math.round(i);i=(i>255?255:(i<0?0:i)).toString(16);return i.length===1?"0"+i:i}).join("")},mix:function(color2,weight){color1=this;var p=weight;var w=p*2-1;var a=color1.toHSL().a-color2.toHSL().a;var w1=(((w*a==-1)?w:(w+a)/(1+w*a))+1)/2;var w2=1-w1;var rgb=[color1.rgb[0]*w1+color2.rgb[0]*w2,color1.rgb[1]*w1+color2.rgb[1]*w2,color1.rgb[2]*w1+color2.rgb[2]*w2];var alpha=color1.alpha*p+color2.alpha*(1-p);return new Color(rgb,alpha)}};var LinearRamp=function(start_color,end_color,start_value,end_value){this.start_color=new Color(start_color);this.end_color=new Color(end_color);this.start_value=start_value;this.end_value=end_value;this.value_range=end_value-start_value};LinearRamp.prototype.map_value=function(value){value=Math.max(value,this.start_value);value=Math.min(value,this.end_value);value=(value-this.start_value)/this.value_range;return this.start_color.mix(this.end_color,1-value).toCSS()};var SplitRamp=function(start_color,middle_color,end_color,start_value,end_value){this.positive_ramp=new LinearRamp(middle_color,end_color,0,end_value);this.negative_ramp=new LinearRamp(middle_color,start_color,0,-start_value);this.start_value=start_value;this.end_value=end_value};SplitRamp.prototype.map_value=function(value){value=Math.max(value,this.start_value);value=Math.min(value,this.end_value);if(value>=0){return this.positive_ramp.map_value(value)}else{return this.negative_ramp.map_value(-value)}};var DiagonalHeatmapPainter=function(data,view_start,view_end,prefs,mode){Painter.call(this,data,view_start,view_end,prefs,mode);var i,len;if(this.prefs.min_value===undefined){var min_value=Infinity;for(i=0,len=this.data.length;i<len;i++){min_value=Math.min(min_value,this.data[i][5])}this.prefs.min_value=min_value}if(this.prefs.max_value===undefined){var max_value=-Infinity;for(i=0,len=this.data.length;i<len;i++){max_value=Math.max(max_value,this.data[i][5])}this.prefs.max_value=max_value}};DiagonalHeatmapPainter.prototype.default_prefs={min_value:undefined,max_value:undefined,mode:"Heatmap",pos_color:"#FF8C00",neg_color:"#4169E1"};DiagonalHeatmapPainter.prototype.draw=function(ctx,width,height,w_scale){var min_value=this.prefs.min_value,max_value=this.prefs.max_value,value_range=max_value-min_value,height_px=height,view_start=this.view_start,mode=this.mode,data=this.data,invsqrt2=1/Math.sqrt(2);var ramp=(new SplitRamp(this.prefs.neg_color,"#FFFFFF",this.prefs.pos_color,min_value,max_value));var d,s1,e1,s2,e2,value;var scale=function(p){return(p-view_start)*w_scale};ctx.save();ctx.rotate(-45*Math.PI/180);ctx.scale(invsqrt2,invsqrt2);for(var i=0,len=data.length;i<len;i++){d=data[i];s1=scale(d[1]);e1=scale(d[2]);s2=scale(d[4]);e2=scale(d[5]);value=d[6];ctx.fillStyle=(ramp.map_value(value));ctx.fillRect(s1,s2,(e1-s1),(e2-s2))}ctx.restore()};var VariantPainter=function(data,view_start,view_end,prefs,mode,base_color_fn){Painter.call(this,data,view_start,view_end,prefs,mode);this.base_color_fn=base_color_fn;this.divider_height=1};extend(VariantPainter.prototype,Painter.prototype,{get_row_height:function(){var mode=this.mode,height;if(mode==="Dense"){height=DENSE_TRACK_HEIGHT}else{if(mode==="Squish"){height=SQUISH_TRACK_HEIGHT}else{height=PACK_TRACK_HEIGHT}}return height},get_required_height:function(rows_required,width){var height=this.prefs.summary_height;if(this.prefs.show_sample_data){height+=this.divider_height;if(this.data.length!==0){height+=(this.data[0][7].match(/,/g).length+1)*this.get_row_height()}}return height},draw:function(ctx,width,height,w_scale){var locus_data,pos,id,ref,alt,qual,filter,sample_gts,allele_counts,variant,draw_x_start,char_x_start,draw_y_start,genotype,base_px=Math.max(1,Math.floor(w_scale)),row_height=(this.mode==="Squish"?SQUISH_TRACK_HEIGHT:PACK_TRACK_HEIGHT),feature_height=(w_scale<0.1?row_height:(this.mode==="Squish"?SQUISH_FEATURE_HEIGHT:PACK_FEATURE_HEIGHT)),j;if(this.prefs.show_sample_data){ctx.fillStyle="#F3F3F3";ctx.globalAlpha=1;ctx.fillRect(0,this.prefs.summary_height-this.divider_height,width,this.divider_height)}ctx.textAlign="center";for(var i=0;i<this.data.length;i++){locus_data=this.data[i];pos=locus_data[1];alt=locus_data[4].split(",");sample_gts=locus_data[7].split(",");allele_counts=locus_data.slice(8);draw_x_start=Math.floor(Math.max(-0.5*w_scale,(pos-this.view_start-0.5)*w_scale));char_x_start=Math.floor(Math.max(0,(pos-this.view_start)*w_scale));ctx.fillStyle="#999999";ctx.fillRect(draw_x_start,0,base_px,this.prefs.summary_height);draw_y_start=this.prefs.summary_height;for(j=0;j<alt.length;j++){ctx.fillStyle=this.base_color_fn(alt[j]);allele_frac=allele_counts/sample_gts.length;draw_height=Math.ceil(this.prefs.summary_height*allele_frac);ctx.fillRect(draw_x_start,draw_y_start-draw_height,base_px,draw_height);draw_y_start-=draw_height}if(!this.prefs.show_sample_data){continue}draw_y_start=this.prefs.summary_height+this.divider_height;for(j=0;j<sample_gts.length;j++,draw_y_start+=row_height){genotype=(sample_gts[j]?sample_gts[j].split(/\/|\|/):["0","0"]);variant=null;if(genotype[0]===genotype[1]){if(genotype[0]==="."){}else{if(genotype[0]!=="0"){variant=alt[parseInt(genotype[0],10)-1];ctx.globalAlpha=1}}}else{variant=(genotype[0]!=="0"?genotype[0]:genotype[1]);variant=alt[parseInt(variant,10)-1];ctx.globalAlpha=0.4}if(variant){ctx.fillStyle=this.base_color_fn(variant);if(this.mode==="Squish"||w_scale<ctx.canvas.manager.char_width_px){ctx.fillRect(draw_x_start,draw_y_start+1,base_px,feature_height)}else{ctx.fillText(variant,char_x_start,draw_y_start+row_height)}}}}}});return{Scaler:Scaler,SummaryTreePainter:SummaryTreePainter,LinePainter:LinePainter,LinkedFeaturePainter:LinkedFeaturePainter,ReadPainter:ReadPainter,RefBasedReadPainter:RefBasedReadPainter,ArcLinkedFeaturePainter:ArcLinkedFeaturePainter,DiagonalHeatmapPainter:DiagonalHeatmapPainter,VariantPainter:VariantPainter}});
\ No newline at end of file
+define(["libs/underscore"],function(_){var extend=_.extend;var BEFORE=1001,CONTAINS=1002,OVERLAP_START=1003,OVERLAP_END=1004,CONTAINED_BY=1005,AFTER=1006;var compute_overlap=function(first_region,second_region){var first_start=first_region[0],first_end=first_region[1],second_start=second_region[0],second_end=second_region[1],overlap;if(first_start<second_start){if(first_end<=second_start){overlap=BEFORE}else{if(first_end<=second_end){overlap=OVERLAP_START}else{overlap=CONTAINS}}}else{if(first_start>second_end){overlap=AFTER}else{if(first_end<=second_end){overlap=CONTAINED_BY}else{overlap=OVERLAP_END}}}return overlap};var is_overlap=function(first_region,second_region){var overlap=compute_overlap(first_region,second_region);return(overlap!==BEFORE&&overlap!==AFTER)};var dashedLine=function(ctx,x1,y1,x2,y2,dashLen){if(dashLen===undefined){dashLen=4}var dX=x2-x1;var dY=y2-y1;var dashes=Math.floor(Math.sqrt(dX*dX+dY*dY)/dashLen);var dashX=dX/dashes;var dashY=dY/dashes;var q;for(q=0;q<dashes;q++,x1+=dashX,y1+=dashY){if(q%2!==0){continue}ctx.fillRect(x1,y1,dashLen,1)}};var drawDownwardEquilateralTriangle=function(ctx,down_vertex_x,down_vertex_y,side_len){var x1=down_vertex_x-side_len/2,x2=down_vertex_x+side_len/2,y=down_vertex_y-Math.sqrt(side_len*3/2);ctx.beginPath();ctx.moveTo(x1,y);ctx.lineTo(x2,y);ctx.lineTo(down_vertex_x,down_vertex_y);ctx.lineTo(x1,y);ctx.strokeStyle=this.fillStyle;ctx.fill();ctx.stroke();ctx.closePath()};var Scaler=function(default_val){this.default_val=(default_val?default_val:1)};Scaler.prototype.gen_val=function(input){return this.default_val};var Painter=function(data,view_start,view_end,prefs,mode){this.data=data;this.view_start=view_start;this.view_end=view_end;this.prefs=extend({},this.default_prefs,prefs);this.mode=mode};Painter.prototype.default_prefs={};Painter.prototype.draw=function(ctx,width,height,w_scale){};var SummaryTreePainter=function(data,view_start,view_end,prefs,mode){Painter.call(this,data,view_start,view_end,prefs,mode)};SummaryTreePainter.prototype.default_prefs={show_counts:false};SummaryTreePainter.prototype.draw=function(ctx,width,height,w_scale){var view_start=this.view_start,points=this.data.data,max=(this.prefs.histogram_max?this.prefs.histogram_max:this.data.max),base_y=height,delta_x_px=Math.ceil(this.data.delta*w_scale);ctx.save();for(var i=0,len=points.length;i<len;i++){var x=Math.floor((points[i][0]-view_start)*w_scale);var y=points[i][1];if(!y){continue}var y_px=y/max*height;if(y!==0&&y_px<1){y_px=1}ctx.fillStyle=this.prefs.block_color;ctx.fillRect(x,base_y-y_px,delta_x_px,y_px);var text_padding_req_x=4;if(this.prefs.show_counts&&(ctx.measureText(y).width+text_padding_req_x)<delta_x_px){ctx.fillStyle=this.prefs.label_color;ctx.textAlign="center";ctx.fillText(y,x+(delta_x_px/2),10)}}ctx.restore()};var LinePainter=function(data,view_start,view_end,prefs,mode){Painter.call(this,data,view_start,view_end,prefs,mode);var i,len;if(this.prefs.min_value===undefined){var min_value=Infinity;for(i=0,len=this.data.length;i<len;i++){min_value=Math.min(min_value,this.data[i][1])}this.prefs.min_value=min_value}if(this.prefs.max_value===undefined){var max_value=-Infinity;for(i=0,len=this.data.length;i<len;i++){max_value=Math.max(max_value,this.data[i][1])}this.prefs.max_value=max_value}};LinePainter.prototype.default_prefs={min_value:undefined,max_value:undefined,mode:"Histogram",color:"#000",overflow_color:"#F66"};LinePainter.prototype.draw=function(ctx,width,height,w_scale){var in_path=false,min_value=this.prefs.min_value,max_value=this.prefs.max_value,vertical_range=max_value-min_value,height_px=height,view_start=this.view_start,mode=this.mode,data=this.data;ctx.save();var y_zero=Math.round(height+min_value/vertical_range*height);if(mode!=="Intensity"){ctx.fillStyle="#aaa";ctx.fillRect(0,y_zero,width,1)}ctx.beginPath();var x_scaled,y,delta_x_px;if(data.length>1){delta_x_px=Math.ceil((data[1][0]-data[0][0])*w_scale)}else{delta_x_px=10}var pref_color=parseInt(this.prefs.color.slice(1),16),pref_r=(pref_color&16711680)>>16,pref_g=(pref_color&65280)>>8,pref_b=pref_color&255;for(var i=0,len=data.length;i<len;i++){ctx.fillStyle=ctx.strokeStyle=this.prefs.color;x_scaled=Math.round((data[i][0]-view_start-0.5)*w_scale);y=data[i][1];var top_overflow=false,bot_overflow=false;if(y===null){if(in_path&&mode==="Filled"){ctx.lineTo(x_scaled,height_px)}in_path=false;continue}if(y<min_value){bot_overflow=true;y=min_value}else{if(y>max_value){top_overflow=true;y=max_value}}if(mode==="Histogram"){y=Math.round(y/vertical_range*height_px);ctx.fillRect(x_scaled,y_zero,delta_x_px,-y)}else{if(mode==="Intensity"){var saturation=(y-min_value)/vertical_range,new_r=Math.round(pref_r+(255-pref_r)*(1-saturation)),new_g=Math.round(pref_g+(255-pref_g)*(1-saturation)),new_b=Math.round(pref_b+(255-pref_b)*(1-saturation));ctx.fillStyle="rgb("+new_r+","+new_g+","+new_b+")";ctx.fillRect(x_scaled,0,delta_x_px,height_px)}else{y=Math.round(height_px-(y-min_value)/vertical_range*height_px);if(in_path){ctx.lineTo(x_scaled,y)}else{in_path=true;if(mode==="Filled"){ctx.moveTo(x_scaled,height_px);ctx.lineTo(x_scaled,y)}else{ctx.moveTo(x_scaled,y)}}}}ctx.fillStyle=this.prefs.overflow_color;if(top_overflow||bot_overflow){var overflow_x;if(mode==="Histogram"||mode==="Intensity"){overflow_x=delta_x_px}else{x_scaled-=2;overflow_x=4}if(top_overflow){ctx.fillRect(x_scaled,0,overflow_x,3)}if(bot_overflow){ctx.fillRect(x_scaled,height_px-3,overflow_x,3)}}ctx.fillStyle=this.prefs.color}if(mode==="Filled"){if(in_path){ctx.lineTo(x_scaled,y_zero);ctx.lineTo(0,y_zero)}ctx.fill()}else{ctx.stroke()}ctx.restore()};var FeaturePositionMapper=function(slot_height){this.feature_positions={};this.slot_height=slot_height;this.translation=0;this.y_translation=0};FeaturePositionMapper.prototype.map_feature_data=function(feature_data,slot,x_start,x_end){if(!this.feature_positions[slot]){this.feature_positions[slot]=[]}this.feature_positions[slot].push({data:feature_data,x_start:x_start,x_end:x_end})};FeaturePositionMapper.prototype.get_feature_data=function(x,y){var slot=Math.floor((y-this.y_translation)/this.slot_height),feature_dict;if(!this.feature_positions[slot]){return null}x+=this.translation;for(var i=0;i<this.feature_positions[slot].length;i++){feature_dict=this.feature_positions[slot][i];if(x>=feature_dict.x_start&&x<=feature_dict.x_end){return feature_dict.data}}};var FeaturePainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler){Painter.call(this,data,view_start,view_end,prefs,mode);this.alpha_scaler=(alpha_scaler?alpha_scaler:new Scaler());this.height_scaler=(height_scaler?height_scaler:new Scaler())};FeaturePainter.prototype.default_prefs={block_color:"#FFF",connector_color:"#FFF"};extend(FeaturePainter.prototype,{get_required_height:function(rows_required,width){var required_height=this.get_row_height(),y_scale=required_height,mode=this.mode;if(mode==="no_detail"||mode==="Squish"||mode==="Pack"){required_height=rows_required*y_scale}return required_height+this.get_top_padding(width)+this.get_bottom_padding(width)},get_top_padding:function(width){return 0},get_bottom_padding:function(width){return Math.max(Math.round(this.get_row_height()/2),5)},draw:function(ctx,width,height,w_scale,slots){var data=this.data,view_start=this.view_start,view_end=this.view_end;ctx.save();ctx.fillStyle=this.prefs.block_color;ctx.textAlign="right";var y_scale=this.get_row_height(),feature_mapper=new FeaturePositionMapper(y_scale),x_draw_coords;for(var i=0,len=data.length;i<len;i++){var feature=data[i],feature_uid=feature[0],feature_start=feature[1],feature_end=feature[2],slot=(slots&&slots[feature_uid]!==undefined?slots[feature_uid]:null);if((feature_start<view_end&&feature_end>view_start)&&(this.mode==="Dense"||slot!==null)){x_draw_coords=this.draw_element(ctx,this.mode,feature,slot,view_start,view_end,w_scale,y_scale,width);feature_mapper.map_feature_data(feature,slot,x_draw_coords[0],x_draw_coords[1])}}ctx.restore();feature_mapper.y_translation=this.get_top_padding(width);return feature_mapper},draw_element:function(ctx,mode,feature,slot,tile_low,tile_high,w_scale,y_scale,width){console.log("WARNING: Unimplemented function.");return[0,0]}});var DENSE_TRACK_HEIGHT=10,NO_DETAIL_TRACK_HEIGHT=3,SQUISH_TRACK_HEIGHT=5,PACK_TRACK_HEIGHT=10,NO_DETAIL_FEATURE_HEIGHT=1,DENSE_FEATURE_HEIGHT=9,SQUISH_FEATURE_HEIGHT=3,PACK_FEATURE_HEIGHT=9,LABEL_SPACING=2,CONNECTOR_COLOR="#ccc";var LinkedFeaturePainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler){FeaturePainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler);this.draw_background_connector=true;this.draw_individual_connectors=false};extend(LinkedFeaturePainter.prototype,FeaturePainter.prototype,{get_row_height:function(){var mode=this.mode,height;if(mode==="Dense"){height=DENSE_TRACK_HEIGHT}else{if(mode==="no_detail"){height=NO_DETAIL_TRACK_HEIGHT}else{if(mode==="Squish"){height=SQUISH_TRACK_HEIGHT}else{height=PACK_TRACK_HEIGHT}}}return height},draw_element:function(ctx,mode,feature,slot,tile_low,tile_high,w_scale,y_scale,width){var feature_uid=feature[0],feature_start=feature[1],feature_end=feature[2],feature_name=feature[3],feature_strand=feature[4],f_start=Math.floor(Math.max(0,(feature_start-tile_low-0.5)*w_scale)),f_end=Math.ceil(Math.min(width,Math.max(0,(feature_end-tile_low-0.5)*w_scale))),draw_start=f_start,draw_end=f_end,y_center=(mode==="Dense"?0:(0+slot))*y_scale+this.get_top_padding(width),thickness,y_start,thick_start=null,thick_end=null,block_color=(!feature_strand||feature_strand==="+"||feature_strand==="."?this.prefs.block_color:this.prefs.reverse_strand_color);label_color=this.prefs.label_color;ctx.globalAlpha=this.alpha_scaler.gen_val(feature);if(mode==="Dense"){slot=1}if(mode==="no_detail"){ctx.fillStyle=block_color;ctx.fillRect(f_start,y_center+5,f_end-f_start,NO_DETAIL_FEATURE_HEIGHT)}else{var feature_ts=feature[5],feature_te=feature[6],feature_blocks=feature[7],full_height=true;if(feature_ts&&feature_te){thick_start=Math.floor(Math.max(0,(feature_ts-tile_low)*w_scale));thick_end=Math.ceil(Math.min(width,Math.max(0,(feature_te-tile_low)*w_scale)))}var thin_height,thick_height;if(mode==="Squish"){thin_height=1;thick_height=SQUISH_FEATURE_HEIGHT;full_height=false}else{if(mode==="Dense"){thin_height=5;thick_height=DENSE_FEATURE_HEIGHT}else{thin_height=5;thick_height=PACK_FEATURE_HEIGHT}}if(!feature_blocks){ctx.fillStyle=block_color;ctx.fillRect(f_start,y_center+1,f_end-f_start,thick_height);if(feature_strand&&full_height){if(feature_strand==="+"){ctx.fillStyle=ctx.canvas.manager.get_pattern("right_strand_inv")}else{if(feature_strand==="-"){ctx.fillStyle=ctx.canvas.manager.get_pattern("left_strand_inv")}}ctx.fillRect(f_start,y_center+1,f_end-f_start,thick_height)}}else{var cur_y_center,cur_height;if(mode==="Squish"||mode==="Dense"){cur_y_center=y_center+Math.floor(SQUISH_FEATURE_HEIGHT/2)+1;cur_height=1}else{if(feature_strand){cur_y_center=y_center;cur_height=thick_height}else{cur_y_center+=(SQUISH_FEATURE_HEIGHT/2)+1;cur_height=1}}if(this.draw_background_connector){if(mode==="Squish"||mode==="Dense"){ctx.fillStyle=CONNECTOR_COLOR}else{if(feature_strand){if(feature_strand==="+"){ctx.fillStyle=ctx.canvas.manager.get_pattern("right_strand")}else{if(feature_strand==="-"){ctx.fillStyle=ctx.canvas.manager.get_pattern("left_strand")}}}else{ctx.fillStyle=CONNECTOR_COLOR}}ctx.fillRect(f_start,cur_y_center,f_end-f_start,cur_height)}var start_and_height;for(var k=0,k_len=feature_blocks.length;k<k_len;k++){var block=feature_blocks[k],block_start=Math.floor(Math.max(0,(block[0]-tile_low-0.5)*w_scale)),block_end=Math.ceil(Math.min(width,Math.max((block[1]-tile_low-0.5)*w_scale))),last_block_start,last_block_end;if(block_start>block_end){continue}ctx.fillStyle=block_color;ctx.fillRect(block_start,y_center+(thick_height-thin_height)/2+1,block_end-block_start,thin_height);if(thick_start!==undefined&&feature_te>feature_ts&&!(block_start>thick_end||block_end<thick_start)){var block_thick_start=Math.max(block_start,thick_start),block_thick_end=Math.min(block_end,thick_end);ctx.fillRect(block_thick_start,y_center+1,block_thick_end-block_thick_start,thick_height);if(feature_blocks.length===1&&mode==="Pack"){if(feature_strand==="+"){ctx.fillStyle=ctx.canvas.manager.get_pattern("right_strand_inv")}else{if(feature_strand==="-"){ctx.fillStyle=ctx.canvas.manager.get_pattern("left_strand_inv")}}if(block_thick_start+14<block_thick_end){block_thick_start+=2;block_thick_end-=2}ctx.fillRect(block_thick_start,y_center+1,block_thick_end-block_thick_start,thick_height)}}if(this.draw_individual_connectors&&last_block_start){this.draw_connector(ctx,last_block_start,last_block_end,block_start,block_end,y_center)}last_block_start=block_start;last_block_end=block_end}if(mode==="Pack"){ctx.globalAlpha=1;ctx.fillStyle="white";var hscale_factor=this.height_scaler.gen_val(feature),new_height=Math.ceil(thick_height*hscale_factor),ws_height=Math.round((thick_height-new_height)/2);if(hscale_factor!==1){ctx.fillRect(f_start,cur_y_center+1,f_end-f_start,ws_height);ctx.fillRect(f_start,cur_y_center+thick_height-ws_height+1,f_end-f_start,ws_height)}}}ctx.globalAlpha=1;if(feature_name&&mode==="Pack"&&feature_start>tile_low){ctx.fillStyle=label_color;if(tile_low===0&&f_start-ctx.measureText(feature_name).width<0){ctx.textAlign="left";ctx.fillText(feature_name,f_end+LABEL_SPACING,y_center+8);draw_end+=ctx.measureText(feature_name).width+LABEL_SPACING}else{ctx.textAlign="right";ctx.fillText(feature_name,f_start-LABEL_SPACING,y_center+8);draw_start-=ctx.measureText(feature_name).width+LABEL_SPACING}}}ctx.globalAlpha=1;return[draw_start,draw_end]}});var ReadPainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler,ref_seq,base_color_fn){FeaturePainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler);this.ref_seq=(ref_seq?ref_seq.data:null);this.base_color_fn=base_color_fn};extend(ReadPainter.prototype,FeaturePainter.prototype,{get_row_height:function(){var height,mode=this.mode;if(mode==="Dense"){height=DENSE_TRACK_HEIGHT}else{if(mode==="Squish"){height=SQUISH_TRACK_HEIGHT}else{height=PACK_TRACK_HEIGHT;if(this.prefs.show_insertions){height*=2}}}return height},_parse_cigar:function(cigar_str){var cigar_ops="MIDNSHP=X";var blocks=[[0,0]],cur_block=blocks[0],base_pos=0,parsed_cigar=_.map(cigar_str.match(/[0-9]+[MIDNSHP=X]/g),function(op){var op_len=parseInt(op.slice(0,-1),10),op_char=op.slice(-1);if(op_char==="N"){if(cur_block[1]!==0){cur_block=[base_pos+op_len,base_pos+op_len];blocks.push(cur_block)}}else{if("ISHP".indexOf(op_char)===-1){cur_block[1]+=op_len;base_pos+=op_len}}return[cigar_ops.indexOf(op_char),op_len]});return{blocks:blocks,cigar:parsed_cigar}},draw_read:function(ctx,mode,w_scale,y_center,tile_low,tile_high,feature_start,cigar,strand,read_seq){ctx.textAlign="center";var tile_region=[tile_low,tile_high],base_offset=0,seq_offset=0,gap=Math.round(w_scale/2),char_width_px=ctx.canvas.manager.char_width_px,block_color=(strand==="+"?this.prefs.block_color:this.prefs.reverse_strand_color),pack_mode=(mode==="Pack");var draw_last=[];if(!cigar){cigar=[[0,read_seq.length]]}for(var cig_id=0,len=cigar.length;cig_id<len;cig_id++){var cig=cigar[cig_id],cig_op="MIDNSHP=X"[cig[0]],cig_len=cig[1];var seq_start=feature_start+base_offset,s_start=Math.floor(Math.max(-0.5*w_scale,(seq_start-tile_low-0.5)*w_scale)),s_end=Math.floor(Math.max(0,(seq_start+cig_len-tile_low-0.5)*w_scale));if(s_start===s_end){s_end+=1}switch(cig_op){case"H":break;case"S":seq_offset+=cig_len;break;case"M":case"=":case"X":if(is_overlap([seq_start,seq_start+cig_len],tile_region)){ctx.fillStyle=block_color;ctx.fillRect(s_start,y_center+(pack_mode?1:4),s_end-s_start,(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT));var seq=read_seq.slice(seq_offset,seq_offset+cig_len),ref_char,read_char;for(var c=0,str_len=seq.length;c<str_len;c++){if(seq_start+c>=tile_low&&seq_start+c<=tile_high){ref_char=(this.ref_seq?this.ref_seq[seq_start-tile_low+c]:null);read_char=seq[c];if((ref_char&&(!this.prefs.show_differences||(read_char.toLowerCase!=="n"&&(ref_char.toLowerCase()!==read_char.toLowerCase()))))||(!ref_char&&!this.prefs.show_differences)){var c_start=Math.floor(Math.max(0,(seq_start+c-tile_low)*w_scale));ctx.fillStyle=this.base_color_fn(seq[c]);if(pack_mode&&w_scale>char_width_px){ctx.fillText(seq[c],c_start,y_center+9)}else{if(w_scale>0.05){ctx.fillRect(c_start-gap,y_center+(pack_mode?1:4),Math.max(1,Math.round(w_scale)),(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT))}}}}}}seq_offset+=cig_len;base_offset+=cig_len;break;case"N":ctx.fillStyle=CONNECTOR_COLOR;ctx.fillRect(s_start,y_center+5,s_end-s_start,1);base_offset+=cig_len;break;case"D":ctx.fillStyle="black";ctx.fillRect(s_start,y_center+4,s_end-s_start,3);base_offset+=cig_len;break;case"P":break;case"I":var insert_x_coord=s_start-gap;if(is_overlap([seq_start,seq_start+cig_len],tile_region)){var seq=read_seq.slice(seq_offset,seq_offset+cig_len);if(this.prefs.show_insertions){var x_center=s_start-(s_end-s_start)/2;if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){ctx.fillStyle="yellow";ctx.fillRect(x_center-gap,y_center-9,s_end-s_start,9);draw_last[draw_last.length]={type:"triangle",data:[insert_x_coord,y_center+4,5]};ctx.fillStyle=CONNECTOR_COLOR;switch(compute_overlap([seq_start,seq_start+cig_len],tile_region)){case (OVERLAP_START):seq=seq.slice(tile_low-seq_start);break;case (OVERLAP_END):seq=seq.slice(0,seq_start-tile_high);break;case (CONTAINED_BY):break;case (CONTAINS):seq=seq.slice(tile_low-seq_start,seq_start-tile_high);break}for(var c=0,str_len=seq.length;c<str_len;c++){var c_start=Math.floor(Math.max(0,(seq_start+c-tile_low)*w_scale));ctx.fillText(seq[c],c_start-(s_end-s_start)/2,y_center)}}else{ctx.fillStyle="yellow";ctx.fillRect(x_center,y_center+(this.mode!=="Dense"?2:5),s_end-s_start,(mode!=="Dense"?SQUISH_FEATURE_HEIGHT:DENSE_FEATURE_HEIGHT))}}else{if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){draw_last.push({type:"text",data:[seq.length,insert_x_coord,y_center+9]})}else{}}}seq_offset+=cig_len;break}}ctx.fillStyle="yellow";var item,type,data;for(var i=0;i<draw_last.length;i++){item=draw_last[i];type=item.type;data=item.data;if(type==="text"){ctx.save();ctx.font="bold "+ctx.font;ctx.fillText(data[0],data[1],data[2]);ctx.restore()}else{if(type==="triangle"){drawDownwardEquilateralTriangle(ctx,data[0],data[1],data[2])}}}},draw_element:function(ctx,mode,feature,slot,tile_low,tile_high,w_scale,y_scale,width){var feature_uid=feature[0],feature_start=feature[1],feature_end=feature[2],feature_name=feature[3],f_start=Math.floor(Math.max(-0.5*w_scale,(feature_start-tile_low-0.5)*w_scale)),f_end=Math.ceil(Math.min(width,Math.max(0,(feature_end-tile_low-0.5)*w_scale))),y_center=(mode==="Dense"?0:(0+slot))*y_scale,label_color=this.prefs.label_color;if(feature[5] instanceof Array){var b1_start=Math.floor(Math.max(0,(feature[4][0]-tile_low)*w_scale)),b1_end=Math.ceil(Math.min(width,Math.max(0,(feature[4][1]-tile_low)*w_scale))),b2_start=Math.floor(Math.max(0,(feature[5][0]-tile_low)*w_scale)),b2_end=Math.ceil(Math.min(width,Math.max(0,(feature[5][1]-tile_low)*w_scale))),connector=true;if(feature[4][1]>=tile_low&&feature[4][0]<=tile_high&&feature[4][2]){this.draw_read(ctx,mode,w_scale,y_center,tile_low,tile_high,feature[4][0],feature[4][2],feature[4][3],feature[4][4])}else{connector=false}if(feature[5][1]>=tile_low&&feature[5][0]<=tile_high&&feature[5][2]){this.draw_read(ctx,mode,w_scale,y_center,tile_low,tile_high,feature[5][0],feature[5][2],feature[5][3],feature[5][4])}else{connector=false}if(connector&&b2_start>b1_end){ctx.fillStyle=CONNECTOR_COLOR;dashedLine(ctx,b1_end,y_center+5,b2_start,y_center+5)}}else{this.draw_read(ctx,mode,w_scale,y_center,tile_low,tile_high,feature_start,feature[4],feature[5],feature[6])}if(mode==="Pack"&&feature_start>=tile_low&&feature_name!=="."){ctx.fillStyle=this.prefs.label_color;if(tile_low===0&&f_start-ctx.measureText(feature_name).width<0){ctx.textAlign="left";ctx.fillText(feature_name,f_end+LABEL_SPACING,y_center+8)}else{ctx.textAlign="right";ctx.fillText(feature_name,f_start-LABEL_SPACING,y_center+8)}}return[0,0]}});var RefBasedReadPainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler,ref_seq,base_color_fn){ReadPainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler,ref_seq,base_color_fn)};extend(RefBasedReadPainter.prototype,ReadPainter.prototype,FeaturePainter,{draw_read:function(ctx,mode,w_scale,y_center,tile_low,tile_high,feature_start,cigar,strand,read_seq){ctx.textAlign="center";var tile_region=[tile_low,tile_high],base_offset=0,seq_offset=0,gap=Math.round(w_scale/2),char_width_px=ctx.canvas.manager.char_width_px,block_color=(strand==="+"?this.prefs.block_color:this.prefs.reverse_strand_color),pack_mode=(mode==="Pack"),drawing_blocks=[];var draw_last=[];var t=this._parse_cigar(cigar);cigar=t.cigar;drawing_blocks=t.blocks;for(var i=0;i<drawing_blocks.length;i++){var block=drawing_blocks[i];if(is_overlap([feature_start+block[0],feature_start+block[1]],tile_region)){var s_start=Math.floor(Math.max(-0.5*w_scale,(feature_start+block[0]-tile_low-0.5)*w_scale)),s_end=Math.floor(Math.max(0,(feature_start+block[1]-tile_low-0.5)*w_scale));if(s_start===s_end){s_end+=1}ctx.fillStyle=block_color;ctx.fillRect(s_start,y_center+(pack_mode?1:4),s_end-s_start,(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT))}}for(var cig_id=0,len=cigar.length;cig_id<len;cig_id++){var cig=cigar[cig_id],cig_op="MIDNSHP=X"[cig[0]],cig_len=cig[1];var seq_start=feature_start+base_offset,s_start=Math.floor(Math.max(0,-0.5*w_scale,(seq_start-tile_low-0.5)*w_scale)),s_end=Math.floor(Math.max(0,(seq_start+cig_len-tile_low-0.5)*w_scale));if(s_start===s_end){s_end+=1}switch(cig_op){case"H":case"S":case"P":break;case"M":base_offset+=cig_len;break;case"=":case"X":if(is_overlap([seq_start,seq_start+cig_len],tile_region)){var cur_seq="";if(cig_op==="X"){cur_seq=read_seq.slice(seq_offset,seq_offset+cig_len)}else{if(this.ref_seq){cur_seq=this.ref_seq.slice(Math.max(0,seq_start-tile_low),Math.min(seq_start-tile_low+cig_len,tile_high-tile_low))}}var start_pos=Math.max(seq_start,tile_low);for(var c=0;c<cur_seq.length;c++){if(cur_seq&&!this.prefs.show_differences||cig_op==="X"){var c_start=Math.floor(Math.max(0,(start_pos+c-tile_low)*w_scale));ctx.fillStyle=this.base_color_fn(cur_seq[c]);if(pack_mode&&w_scale>char_width_px){ctx.fillText(cur_seq[c],c_start,y_center+9)}else{if(w_scale>0.05){ctx.fillRect(c_start-gap,y_center+(pack_mode?1:4),Math.max(1,Math.round(w_scale)),(pack_mode?PACK_FEATURE_HEIGHT:SQUISH_FEATURE_HEIGHT))}}}}}if(cig_op==="X"){seq_offset+=cig_len}base_offset+=cig_len;break;case"N":ctx.fillStyle=CONNECTOR_COLOR;ctx.fillRect(s_start,y_center+5,s_end-s_start,1);base_offset+=cig_len;break;case"D":ctx.fillStyle="black";ctx.fillRect(s_start,y_center+4,s_end-s_start,3);base_offset+=cig_len;break;case"I":var insert_x_coord=s_start-gap;if(is_overlap([seq_start,seq_start+cig_len],tile_region)){var seq=read_seq.slice(seq_offset,seq_offset+cig_len);if(this.prefs.show_insertions){var x_center=s_start-(s_end-s_start)/2;if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){ctx.fillStyle="yellow";ctx.fillRect(x_center-gap,y_center-9,s_end-s_start,9);draw_last[draw_last.length]={type:"triangle",data:[insert_x_coord,y_center+4,5]};ctx.fillStyle=CONNECTOR_COLOR;switch(compute_overlap([seq_start,seq_start+cig_len],tile_region)){case (OVERLAP_START):seq=seq.slice(tile_low-seq_start);break;case (OVERLAP_END):seq=seq.slice(0,seq_start-tile_high);break;case (CONTAINED_BY):break;case (CONTAINS):seq=seq.slice(tile_low-seq_start,seq_start-tile_high);break}for(var c=0,str_len=seq.length;c<str_len;c++){var c_start=Math.floor(Math.max(0,(seq_start+c-tile_low)*w_scale));ctx.fillText(seq[c],c_start-(s_end-s_start)/2,y_center)}}else{ctx.fillStyle="yellow";ctx.fillRect(x_center,y_center+(this.mode!=="Dense"?2:5),s_end-s_start,(mode!=="Dense"?SQUISH_FEATURE_HEIGHT:DENSE_FEATURE_HEIGHT))}}else{if((mode==="Pack"||this.mode==="Auto")&&read_seq!==undefined&&w_scale>char_width_px){draw_last.push({type:"text",data:[seq.length,insert_x_coord,y_center+9]})}else{}}}seq_offset+=cig_len;break}}ctx.fillStyle="yellow";var item,type,data;for(var i=0;i<draw_last.length;i++){item=draw_last[i];type=item.type;data=item.data;if(type==="text"){ctx.save();ctx.font="bold "+ctx.font;ctx.fillText(data[0],data[1],data[2]);ctx.restore()}else{if(type==="triangle"){drawDownwardEquilateralTriangle(ctx,data[0],data[1],data[2])}}}}});var ArcLinkedFeaturePainter=function(data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler){LinkedFeaturePainter.call(this,data,view_start,view_end,prefs,mode,alpha_scaler,height_scaler);this.longest_feature_length=this.calculate_longest_feature_length();this.draw_background_connector=false;this.draw_individual_connectors=true};extend(ArcLinkedFeaturePainter.prototype,FeaturePainter.prototype,LinkedFeaturePainter.prototype,{calculate_longest_feature_length:function(){var longest_feature_length=0;for(var i=0,len=this.data.length;i<len;i++){var feature=this.data[i],feature_start=feature[1],feature_end=feature[2];longest_feature_length=Math.max(longest_feature_length,feature_end-feature_start)}return longest_feature_length},get_top_padding:function(width){var view_range=this.view_end-this.view_start,w_scale=width/view_range;return Math.min(128,Math.ceil((this.longest_feature_length/2)*w_scale))},draw_connector:function(ctx,block1_start,block1_end,block2_start,block2_end,y_center){var x_center=(block1_end+block2_start)/2,radius=block2_start-x_center;var angle1=Math.PI,angle2=0;if(radius>0){ctx.beginPath();ctx.arc(x_center,y_center,block2_start-x_center,Math.PI,0);ctx.stroke()}}});var Color=function(rgb,a){if(Array.isArray(rgb)){this.rgb=rgb}else{if(rgb.length==6){this.rgb=rgb.match(/.{2}/g).map(function(c){return parseInt(c,16)})}else{if(rgb.length==7){this.rgb=rgb.substring(1,7).match(/.{2}/g).map(function(c){return parseInt(c,16)})}else{this.rgb=rgb.split("").map(function(c){return parseInt(c+c,16)})}}}this.alpha=typeof(a)==="number"?a:1};Color.prototype={eval:function(){return this},toCSS:function(){if(this.alpha<1){return"rgba("+this.rgb.map(function(c){return Math.round(c)}).concat(this.alpha).join(", ")+")"}else{return"#"+this.rgb.map(function(i){i=Math.round(i);i=(i>255?255:(i<0?0:i)).toString(16);return i.length===1?"0"+i:i}).join("")}},toHSL:function(){var r=this.rgb[0]/255,g=this.rgb[1]/255,b=this.rgb[2]/255,a=this.alpha;var max=Math.max(r,g,b),min=Math.min(r,g,b);var h,s,l=(max+min)/2,d=max-min;if(max===min){h=s=0}else{s=l>0.5?d/(2-max-min):d/(max+min);switch(max){case r:h=(g-b)/d+(g<b?6:0);break;case g:h=(b-r)/d+2;break;case b:h=(r-g)/d+4;break}h/=6}return{h:h*360,s:s,l:l,a:a}},toARGB:function(){var argb=[Math.round(this.alpha*255)].concat(this.rgb);return"#"+argb.map(function(i){i=Math.round(i);i=(i>255?255:(i<0?0:i)).toString(16);return i.length===1?"0"+i:i}).join("")},mix:function(color2,weight){color1=this;var p=weight;var w=p*2-1;var a=color1.toHSL().a-color2.toHSL().a;var w1=(((w*a==-1)?w:(w+a)/(1+w*a))+1)/2;var w2=1-w1;var rgb=[color1.rgb[0]*w1+color2.rgb[0]*w2,color1.rgb[1]*w1+color2.rgb[1]*w2,color1.rgb[2]*w1+color2.rgb[2]*w2];var alpha=color1.alpha*p+color2.alpha*(1-p);return new Color(rgb,alpha)}};var LinearRamp=function(start_color,end_color,start_value,end_value){this.start_color=new Color(start_color);this.end_color=new Color(end_color);this.start_value=start_value;this.end_value=end_value;this.value_range=end_value-start_value};LinearRamp.prototype.map_value=function(value){value=Math.max(value,this.start_value);value=Math.min(value,this.end_value);value=(value-this.start_value)/this.value_range;return this.start_color.mix(this.end_color,1-value).toCSS()};var SplitRamp=function(start_color,middle_color,end_color,start_value,end_value){this.positive_ramp=new LinearRamp(middle_color,end_color,0,end_value);this.negative_ramp=new LinearRamp(middle_color,start_color,0,-start_value);this.start_value=start_value;this.end_value=end_value};SplitRamp.prototype.map_value=function(value){value=Math.max(value,this.start_value);value=Math.min(value,this.end_value);if(value>=0){return this.positive_ramp.map_value(value)}else{return this.negative_ramp.map_value(-value)}};var DiagonalHeatmapPainter=function(data,view_start,view_end,prefs,mode){Painter.call(this,data,view_start,view_end,prefs,mode);var i,len;if(this.prefs.min_value===undefined){var min_value=Infinity;for(i=0,len=this.data.length;i<len;i++){min_value=Math.min(min_value,this.data[i][5])}this.prefs.min_value=min_value}if(this.prefs.max_value===undefined){var max_value=-Infinity;for(i=0,len=this.data.length;i<len;i++){max_value=Math.max(max_value,this.data[i][5])}this.prefs.max_value=max_value}};DiagonalHeatmapPainter.prototype.default_prefs={min_value:undefined,max_value:undefined,mode:"Heatmap",pos_color:"#FF8C00",neg_color:"#4169E1"};DiagonalHeatmapPainter.prototype.draw=function(ctx,width,height,w_scale){var min_value=this.prefs.min_value,max_value=this.prefs.max_value,value_range=max_value-min_value,height_px=height,view_start=this.view_start,mode=this.mode,data=this.data,invsqrt2=1/Math.sqrt(2);var ramp=(new SplitRamp(this.prefs.neg_color,"#FFFFFF",this.prefs.pos_color,min_value,max_value));var d,s1,e1,s2,e2,value;var scale=function(p){return(p-view_start)*w_scale};ctx.save();ctx.rotate(-45*Math.PI/180);ctx.scale(invsqrt2,invsqrt2);for(var i=0,len=data.length;i<len;i++){d=data[i];s1=scale(d[1]);e1=scale(d[2]);s2=scale(d[4]);e2=scale(d[5]);value=d[6];ctx.fillStyle=(ramp.map_value(value));ctx.fillRect(s1,s2,(e1-s1),(e2-s2))}ctx.restore()};var VariantPainter=function(data,view_start,view_end,prefs,mode,base_color_fn){Painter.call(this,data,view_start,view_end,prefs,mode);this.base_color_fn=base_color_fn;this.divider_height=1};extend(VariantPainter.prototype,Painter.prototype,{get_row_height:function(){var mode=this.mode,height;if(mode==="Dense"){height=DENSE_TRACK_HEIGHT}else{if(mode==="Squish"){height=SQUISH_TRACK_HEIGHT}else{height=PACK_TRACK_HEIGHT}}return height},get_required_height:function(rows_required,width){var height=this.prefs.summary_height;if(this.prefs.show_sample_data){height+=this.divider_height;if(this.data.length!==0){var comma_match=this.data[0][7].match(/,/g);if(comma_match===null){comma_match=1}else{comma_match=comma_match.length+1}height+=(comma_match*this.get_row_height())}}return height},draw:function(ctx,width,height,w_scale){var locus_data,pos,id,ref,alt,qual,filter,sample_gts,allele_counts,variant,draw_x_start,char_x_start,draw_y_start,genotype,base_px=Math.max(1,Math.floor(w_scale)),row_height=(this.mode==="Squish"?SQUISH_TRACK_HEIGHT:PACK_TRACK_HEIGHT),feature_height=(w_scale<0.1?row_height:(this.mode==="Squish"?SQUISH_FEATURE_HEIGHT:PACK_FEATURE_HEIGHT)),j;if(this.prefs.show_sample_data){ctx.fillStyle="#F3F3F3";ctx.globalAlpha=1;ctx.fillRect(0,this.prefs.summary_height-this.divider_height,width,this.divider_height)}ctx.textAlign="center";for(var i=0;i<this.data.length;i++){locus_data=this.data[i];pos=locus_data[1];alt=locus_data[4].split(",");sample_gts=locus_data[7].split(",");allele_counts=locus_data.slice(8);draw_x_start=Math.floor(Math.max(-0.5*w_scale,(pos-this.view_start-0.5)*w_scale));char_x_start=Math.floor(Math.max(0,(pos-this.view_start)*w_scale));ctx.fillStyle="#999999";ctx.fillRect(draw_x_start,0,base_px,this.prefs.summary_height);draw_y_start=this.prefs.summary_height;for(j=0;j<alt.length;j++){ctx.fillStyle=this.base_color_fn(alt[j]);allele_frac=allele_counts/sample_gts.length;draw_height=Math.ceil(this.prefs.summary_height*allele_frac);ctx.fillRect(draw_x_start,draw_y_start-draw_height,base_px,draw_height);draw_y_start-=draw_height}if(!this.prefs.show_sample_data){continue}draw_y_start=this.prefs.summary_height+this.divider_height;for(j=0;j<sample_gts.length;j++,draw_y_start+=row_height){genotype=(sample_gts[j]?sample_gts[j].split(/\/|\|/):["0","0"]);variant=null;if(genotype[0]===genotype[1]){if(genotype[0]==="."){}else{if(genotype[0]!=="0"){variant=alt[parseInt(genotype[0],10)-1];ctx.globalAlpha=1}}}else{variant=(genotype[0]!=="0"?genotype[0]:genotype[1]);variant=alt[parseInt(variant,10)-1];ctx.globalAlpha=0.4}if(variant){ctx.fillStyle=this.base_color_fn(variant);if(this.mode==="Squish"||w_scale<ctx.canvas.manager.char_width_px){ctx.fillRect(draw_x_start,draw_y_start+1,base_px,feature_height)}else{ctx.fillText(variant,char_x_start,draw_y_start+row_height)}}}}}});return{Scaler:Scaler,SummaryTreePainter:SummaryTreePainter,LinePainter:LinePainter,LinkedFeaturePainter:LinkedFeaturePainter,ReadPainter:ReadPainter,RefBasedReadPainter:RefBasedReadPainter,ArcLinkedFeaturePainter:ArcLinkedFeaturePainter,DiagonalHeatmapPainter:DiagonalHeatmapPainter,VariantPainter:VariantPainter}});
\ No newline at end of file
diff -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 -r 90e18fe3eb822d7b9380b554cd7464f083f0e931 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","mvc/data","viz/trackster/filters"],function(ab,x,l,u,L,X,i){var q=ab.extend;var U=function(ac){return("isResolved" in ac)};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();if(ap.offsetY<aq){$(this).insertBefore(ai);var ar=n[ai.attr("id")];ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);var ar=n[ai.attr("id")];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 aa=16,G=9,D=20,A=100,I=12000,R=400,K=5000,w=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.",E="No data for this chrom/contig.",v="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",y="Tool cannot be rerun: ",a="Loading data...",T="Ready for display",Q=10,H=20;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.name=af.name;this.view=ad;this.container=ac;this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name}],saved_values:af.prefs,onchange:function(){this.track.set_name(this.track.config.values.name)}});this.prefs=this.config.values;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.content_visible=true;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.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var af=function(){hide_modal();$(window).unbind("keypress.check_enter_esc")},ac=function(){ad.config.update_from_form($(".dialog-box"));hide_modal();$(window).unbind("keypress.check_enter_esc")},ae=function(ag){if((ag.keyCode||ag.which)===27){af()}else{if((ag.keyCode||ag.which)===13){ac()}}};$(window).bind("keypress.check_enter_esc",ae);show_modal("Configure",ad.config.build_form(),{Cancel:af,OK:ac})}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".bs-tooltip").remove();ac.remove()}}];q(r.prototype,{init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.content_visible){return true}return false},request_draw:function(){},_draw:function(){},to_dict:function(){},set_name:function(ac){this.old_name=this.name;this.name=ac;this.name_div.text(this.name)},revert_name:function(){if(this.old_name){this.name=this.old_name;this.name_div.text(this.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("href","javascript:void(0);").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 z=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(z.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(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac]._draw()}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{name:this.name,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}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});z.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,z.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){$(".bs-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(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.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 c){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".bs-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 af=[];for(var ad=0;ad<this.drawables.length;ad++){af.push(this.drawables[ad].name)}var ae=new f(this.view,this.view,{name:this.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ae,true);ae.request_draw()},add_drawable:function(ac){z.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){z.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(z.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,ae){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].request_draw(ac,ae)}}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});z.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 x.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new F({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(false,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(){x.select_datasets(select_datasets_url,add_track_async_url,{"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("href","javascript:void(0);").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_drawables(),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.values[ac.toLowerCase()+"_color"]}});q(Y.prototype,z.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=w;var ac=this,ad=$.Deferred();$.ajax({url:chrom_url+"/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){ac.add_label_track(new B(ac))}ac.chrom_data=ag.chrom_info;var aj='<option value="">Select Chrom/Contig</option>';for(var ai=0,af=ac.chrom_data.length;ai<af;ai++){var ah=ac.chrom_data[ai].chrom;aj+='<option value="'+ah+'">'+ah+"</option>"}if(ag.prev_chroms){aj+='<option value="previous">Previous '+w+"</option>"}if(ag.next_chroms){aj+='<option value="next">Next '+w+"</option>"}ac.chrom_select.html(aj);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-w});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+w});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();ae.request_redraw(true);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();var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){z.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){z.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(ak,ac,aj,al){var ai=this,ah=(al?[al]:ai.drawables),ae;var ad;for(var ag=0;ag<ah.length;ag++){ad=ah[ag];ae=-1;for(var af=0;af<ai.tracks_to_be_redrawn.length;af++){if(ai.tracks_to_be_redrawn[af][0]===ad){ae=af;break}}if(ae<0){ai.tracks_to_be_redrawn.push([ad,ac,aj])}else{ai.tracks_to_be_redrawn[ag][1]=ac;ai.tracks_to_be_redrawn[ag][2]=aj}}if(!this.requested_redraw){requestAnimationFrame(function(){ai._redraw(ak)});this.requested_redraw=true}},_redraw:function(am){this.requested_redraw=false;var aj=this.low,af=this.high;if(aj<this.max_low){aj=this.max_low}if(af>this.max_high){af=this.max_high}var al=this.high-this.low;if(this.high!==0&&al<this.min_separation){af=aj+this.min_separation}this.low=Math.floor(aj);this.high=Math.ceil(af);this.update_location(this.low,this.high);this.resolution_b_px=(this.high-this.low)/this.viewport_container.width();this.resolution_px_b=1/this.resolution_b_px;var ac=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ai=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var an=13;this.overview_box.css({left:ac,width:Math.max(an,ai)}).show();if(ai<an){this.overview_box.css("left",ac-(an-ai)/2)}if(this.overview_highlight){this.overview_highlight.css({left:ac,width:ai})}if(!am){var ae,ad,ak;for(var ag=0,ah=this.tracks_to_be_redrawn.length;ag<ah;ag++){ae=this.tracks_to_be_redrawn[ag][0];ad=this.tracks_to_be_redrawn[ag][1];ak=this.tracks_to_be_redrawn[ag][2];if(ae){ae._draw(ad,ak)}}this.tracks_to_be_redrawn=[];for(ag=0,ah=this.label_tracks.length;ag<ah;ag++){this.label_tracks[ag]._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(){$(".bs-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=function(ae,aj,af){this.track=ae;this.id=aj.id;this.name=aj.name;this.params=[];var aq=aj.params;for(var ag=0;ag<aq.length;ag++){var al=aq[ag],ad=al.name,ap=al.label,ah=unescape(al.html),ar=al.value,an=al.type;if(an==="number"){this.params.push(new e(ad,ap,ah,(ad in af?af[ad]:ar),al.min,al.max))}else{if(an==="select"){this.params.push(new N(ad,ap,ah,(ad in af?af[ad]:ar)))}else{console.log("WARNING: unrecognized tool parameter type:",ad,an)}}}this.parent_div=$("<div/>").addClass("dynamic-tool").hide();this.parent_div.bind("drag",function(au){au.stopPropagation()}).click(function(au){au.stopPropagation()}).bind("dblclick",function(au){au.stopPropagation()});var ao=$("<div class='tool-name'>").appendTo(this.parent_div).text(this.name);var am=this.params;var ak=this;$.each(this.params,function(av,ay){var ax=$("<div>").addClass("param-row").appendTo(ak.parent_div);var au=$("<div>").addClass("param-label").text(ay.label).appendTo(ax);var aw=$("<div/>").addClass("param-input").html(ay.html).appendTo(ax);aw.find(":input").val(ay.value);$("<div style='clear: both;'/>").appendTo(ax)});this.parent_div.find("input").click(function(){$(this).select()});var at=$("<div>").addClass("param-row").appendTo(this.parent_div);var ai=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(at);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(at);ac.click(function(){ak.run_on_region()});ai.click(function(){ak.run_on_dataset()});if("visible" in af&&af.visible){this.parent_div.show()}};q(s.prototype,{update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},state_dict:function(){var ad={};for(var ac=0;ac<this.params.length;ac++){ad[this.params[ac].name]=this.params[ac].value}ad.visible=this.parent_div.is(":visible");return ad},get_param_values_dict:function(){var ac={};this.parent_div.find(":input").each(function(){var ad=$(this).attr("name"),ae=$(this).val();ac[ad]=ae});return ac},get_param_values:function(){var ac=[];this.parent_div.find(":input").each(function(){var ad=$(this).attr("name"),ae=$(this).val();if(ad){ac[ac.length]=ae}});return ac},run_on_dataset:function(){var ac=this;ac.run({target_dataset_id:this.track.dataset_id,action:"rerun",tool_id:ac.id},null,function(ad){show_modal(ac.name+" is Running",ac.name+" is running on the complete dataset. Tool outputs are in dataset's history.",{Close:hide_modal})})},run_on_region:function(){var ai=new x.GenomeRegion({chrom:this.track.view.chrom,start:this.track.view.low,end:this.track.view.high}),ad={target_dataset_id:this.track.dataset_id,action:"rerun",tool_id:this.id,regions:[ai.toJSON()]},ah=this.track,ae=ad.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ag=new P(view,view,{name:this.name});var af=ah.container.replace_drawable(ah,ag,false);ag.container_div.insertBefore(ah.view.content_div.children()[af]);ag.add_drawable(ah);ah.container_div.appendTo(ag.content_div);ac=ag}else{ac=ah.container}var aj=new ah.constructor(view,ac,{name:ae,hda_ldda:"hda"});aj.init_for_tool_data();aj.change_mode(ah.mode);aj.set_filters_manager(ah.filters_manager.copy(aj));aj.update_icons();ac.add_drawable(aj);aj.tiles_div.text("Starting job.");this.update_params();this.run(ad,aj,function(ak){aj.set_dataset(new X.Dataset(ak));aj.tiles_div.text("Running job.");aj.init()})},run:function(ac,ae,af){ac.inputs=this.get_param_values_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_paths.get("tool_url"),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(y+ag.message)}else{af(ag)}}})}});var N=function(ad,ac,ae,af){this.name=ad;this.label=ac;this.html=$(ae);this.value=af};q(N.prototype,{update_value:function(){this.value=$(this.html).val()}});var e=function(ae,ad,ag,ah,af,ac){N.call(this,ae,ad,ag,ah);this.min=af;this.max=ac};q(e.prototype,N.prototype,{update_value:function(){N.prototype.update_value.call(this);this.value=parseFloat(this.value)}});var C=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};C.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 F=function(ac){this.track=ac.track;this.params=ac.params;this.values={};this.restore_values((ac.saved_values?ac.saved_values:{}));this.onchange=ac.onchange};q(F.prototype,{restore_values:function(ac){var ad=this;$.each(this.params,function(ae,af){if(ac[af.key]!==undefined){ad.values[af.key]=ac[af.key]}else{ad.values[af.key]=af.default_value}})},build_form:function(){var af=this;var ac=$("<div />");var ae;function ad(ak,ag){for(var ao=0;ao<ak.length;ao++){ae=ak[ao];if(ae.hidden){continue}var ai="param_"+ao;var at=af.values[ae.key];var av=$("<div class='form-row' />").appendTo(ag);av.append($("<label />").attr("for",ai).text(ae.label+":"));if(ae.type==="bool"){av.append($('<input type="checkbox" />').attr("id",ai).attr("name",ai).attr("checked",at))}else{if(ae.type==="text"){av.append($('<input type="text"/>').attr("id",ai).val(at).click(function(){$(this).select()}))}else{if(ae.type==="select"){var aq=$("<select />").attr("id",ai);for(var am=0;am<ae.options.length;am++){$("<option/>").text(ae.options[am].label).attr("value",ae.options[am].value).appendTo(aq)}aq.val(at);av.append(aq)}else{if(ae.type==="color"){var au=$("<div/>").appendTo(av),ap=$("<input />").attr("id",ai).attr("name",ai).val(at).css("float","left").appendTo(au).click(function(ax){$(".bs-tooltip").removeClass("in");var aw=$(this).siblings(".bs-tooltip").addClass("in");aw.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top-($(aw).height()/2)+($(this).height()/2)}).show();aw.click(function(ay){ay.stopPropagation()});$(document).bind("click.color-picker",function(){aw.hide();$(document).unbind("click.color-picker")});ax.stopPropagation()}),an=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(au).attr("title","Set new random color").tooltip(),ar=$("<div class='bs-tooltip right' style='position: absolute;' />").appendTo(au).hide(),aj=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(ar),ah=$("<div class='tooltip-arrow'></div>").appendTo(ar),al=$.farbtastic(aj,{width:100,height:100,callback:ap,color:at});au.append($("<div/>").css("clear","both"));(function(aw){an.click(function(){aw.setColor(l.get_random_color())})})(al)}else{av.append($("<input />").attr("id",ai).attr("name",ai).val(at))}}}}if(ae.help){av.append($("<div class='help'/>").text(ae.help))}}}ad(this.params,ac);return ac},update_from_form:function(ac){var ae=this;var ad=false;$.each(this.params,function(af,ah){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="float"){ag=parseFloat(ag)}else{if(ah.type==="int"){ag=parseInt(ag,10)}else{if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}}}if(ag!==ae.values[ah.key]){ae.values[ah.key]=ag;ad=true}}});if(ad){this.onchange();this.track.changed()}}});var b=function(ac,ag,ae,ad,af){this.track=ac;this.region=ag;this.low=ag.get("start");this.high=ag.get("end");this.resolution=ae;this.html_elt=$("<div class='track-tile'/>").append(ad).height($(ad).attr("height"));this.data=af;this.stale=false};b.prototype.predisplay_actions=function(){};var j=function(ac,ah,ae,ad,af,ag){b.call(this,ac,ah,ae,ad,af);this.max_val=ag};q(j.prototype,b.prototype);var O=function(af,an,ag,ae,ai,ap,aj,aq,ad,am){b.call(this,af,an,ag,ae,ai);this.mode=aj;this.all_slotted=ad;this.feature_mapper=am;this.has_icons=false;if(aq){this.has_icons=true;var ak=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:D-1,width:ae.width}).prependTo(this.html_elt);var al=new x.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),ao=ai.length,ah=$("<a href='javascript:void(0);'/>").addClass("icon more-down").attr("title","For speed, only the first "+ao+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a href='javascript:void(0);'/>").addClass("icon more-across").attr("title","For speed, only the first "+ao+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ah.click(function(){ak.stale=true;af.data_manager.get_more_data(al,af.mode,ak.resolution,{},af.data_manager.DEEP_DATA_REQ);$(".bs-tooltip").hide();af.request_draw(true)}).dblclick(function(ar){ar.stopPropagation()});ac.click(function(){ak.stale=true;af.data_manager.get_more_data(al,af.mode,ak.resolution,{},af.data_manager.BROAD_DATA_REQ);$(".bs-tooltip").hide();af.request_draw(true)}).dblclick(function(ar){ar.stopPropagation()})}};q(O.prototype,b.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 ak=at[0],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]}var af=$("<div/>").attr("id",ak).addClass("feature-popup"),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"))-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"))+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=new X.Dataset(ae.dataset);this.dataset_id=this.dataset.get("id");this.hda_ldda=this.dataset.get("hda_ldda");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 x.GenomeDataManager({dataset:this.dataset,genome:new x.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=0;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.dynamic_tool_div.toggle();if(ac.dynamic_tool_div.is(":visible")){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".bs-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(){hide_modal();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new x.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new x.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}hide_modal();window.location.href=galaxy_paths.get("sweepster_url")+"?"+$.param({dataset_id:ac.dataset_id,hda_ldda:ac.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()}}};show_modal("Visualize tool parameter space and output from different parameter settings?",ae,{No:ah,Yes:ad})}},r.prototype.action_icons_def[2]],can_draw:function(){if(this.dataset_id&&r.prototype.can_draw.call(this)){return true}return false},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.name).attr("id",this.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);this.dataset_id=ac.get("id");this.hda_ldda=ac.get("hda_ldda")},on_resize:function(){},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.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.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.values.mode?this.config.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 B){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof S){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof c){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.content_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.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(){show_modal("Trackster Error","<pre>"+ag.message+"</pre>",{Close:hide_modal})}));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(E)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(v);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(T);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when(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(){},get_drawables:function(){return this}});var M=function(ae,ad,af){g.call(this,ae,ad,af);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in af?af.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=("tool" in af&&af.tool?new s(this,af.tool,af.tool_state):null);this.tile_cache=new x.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){this.dynamic_tool_div=this.tool.parent_div;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(af.mode){this.change_mode(af.mode)}};q(M.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){$(".bs-tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw(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(),name:this.name,hda_ldda:this.hda_ldda,dataset_id:this.dataset_id,prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.values.mode=ad;ac.tile_cache.clear();ac.request_draw();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(ad,ac){this.view.request_redraw(false,ad,ac,this)},before_draw:function(){},_draw:function(ad,ao){if(!this.can_draw()){return}var al=this.view.low,ah=this.view.high,aj=ah-al,ae=this.view.container.width(),aq=this.view.resolution_px_b,ag=this.view.resolution_b_px;if(this.is_overview){al=this.view.max_low;ah=this.view.max_high;ag=(view.max_high-view.max_low)/ae;aq=1/ag}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(ag*R)),ak=true,ap=[],ai=function(ar){return(ar&&"track" in ar)};while((ac*R*ag)<ah){var am=this._get_tile_bounds(ac,ag),an=this.draw_helper(ad,am,ag,this.tiles_div,aq);if(ai(an)){ap.push(an)}else{ak=false}ac+=1}if(!ao){this.tiles_div.children(".remove").removeClass("remove").remove()}var af=this;if(ak){this.tiles_div.children(".remove").remove();af.postdraw_actions(ap,ae,aq,ao)}},postdraw_actions:function(ad,ae,ag,ac){var af=ab.find(ad,function(ah){return ah.has_icons});if(af){ab.each(ad,function(ah){if(!ah.has_icons){ah.html_elt.css("padding-top",D)}})}},draw_helper:function(ac,af,ar,ah,ai,ao){var an=this,aw=this._gen_tile_cache_key(ai,af);if(!ao){ao={}}var av=(ac?undefined:an.tile_cache.get_elt(aw));if(av){an.show_tile(av,ah,ai);return av}var al=true;var at=an.data_manager.get_data(af,an.mode,ar,an.data_url_extra_params);if(U(at)){al=false}var aj;if(view.reference_track){aj=view.reference_track.data_manager.get_data(af,an.mode,ar,view.reference_track.data_url_extra_params);if(U(aj)){al=false}else{aj=view.reference_track.data_manager.subset_entry(aj,af)}}if(al){q(at,ao.more_tile_data);var ak=an.mode;if(ak==="Auto"&&an.get_mode){ak=an.get_mode(at);an.update_auto_mode(ak)}var ae=an.view.canvas_manager.new_canvas(),au=af.get("start"),ad=af.get("end"),ap=Math.ceil((ad-au)*ai)+an.left_offset,am=an.get_canvas_height(at,ak,ai,ap);ae.width=ap;ae.height=am;var aq=ae.getContext("2d");aq.translate(this.left_offset,0);var av=an.draw_tile(at,aq,ak,ar,af,ai,aj);if(av!==undefined){an.tile_cache.set_elt(aw,av);an.show_tile(av,ah,ai)}return av}var ag=$.Deferred();$.when(at,aj).then(function(){view.request_redraw(false,false,false,an);ag.resolve()});return ag},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_summary_tree_tile:function(ac,ae,ag,af,ah){var ad=new L.SummaryTreePainter(ac,ag.get("start"),ag.get("end"),this.prefs);ad.draw(ae,ae.canvas.width,ae.canvas.height,ah);return new j(this,ag,af,ae.canvas,ac.data,ac.max)},draw_tile:function(ac,ad,ah,af,ag,ai,ae){console.log("Warning: TiledTrack.draw_tile() not implemented.")},show_tile:function(ae,ah,ai){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ai;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{ah.append(ac)}ae.html_elt.height("auto");this.max_height_px=Math.max(this.max_height_px,ae.html_elt.height());ae.html_elt.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")},_get_tile_bounds:function(ac,ad){var af=Math.floor(ac*R*ad),ag=Math.ceil(R*ad),ae=(af+ag<=this.view.max_high?af+ag:this.view.max_high);return new x.GenomeRegion({chrom:this.view.chrom,start:af,end:ae})},tool_region_and_parameters_str:function(ae){var ac=this,ad=(ae!==undefined?ae.toString():"all");return" - region=["+ad+"], parameters=["+ac.tool.get_param_values().join(", ")+"]"},data_and_mode_compatible:function(ac,ad){return true},can_subset:function(ac){return false},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state";this.normal_postdraw_actions=this.postdraw_actions;this.postdraw_actions=function(ae,af,ah,ac){var ad=this;ad.normal_postdraw_actions(ae,af,ah,ac);ad.dataset_check_type="converted_datasets_state";ad.data_query_wait=K;var ag=new l.ServerStateDeferred({url:ad.dataset_state_url,url_params:{dataset_id:ad.dataset_id,hda_ldda:ad.hda_ldda},interval:ad.data_query_wait,success_fn:function(ai){return ai!=="pending"}});$.when(ag.go()).then(function(){ad.data_manager.set("data_type","data")});ad.postdraw_actions=ad.normal_postdraw_actions}}});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},_draw:function(){var ae=this.view,af=ae.high-ae.low,ai=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/ai)*ai,ag=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ah=(ac-ae.low)/af*ag;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ah-1}));ac+=ai}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){M.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}if(this.drawables.length!==0){this.set_display_modes(this.drawables[0].display_modes,this.drawables[0].mode)}this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,M.prototype,{action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".bs-tooltip").remove();ac.show_group()}}].concat(M.prototype.action_icons_def),to_dict:z.prototype.to_dict,add_drawable:z.prototype.add_drawable,unpack_drawables:z.prototype.unpack_drawables,change_mode:function(ac){M.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,draw_helper:function(ad,ah,av,aj,al,at){var aq=this,aB=this._gen_tile_cache_key(al,ah);if(!at){at={}}var aA=(ad?undefined:aq.tile_cache.get_elt(aB));if(aA){aq.show_tile(aA,aj,al);return aA}var ak=[],aq,ao=true,aw,am;for(var ax=0;ax<this.drawables.length;ax++){aq=this.drawables[ax];aw=aq.data_manager.get_data(ah,aq.mode,av,aq.data_url_extra_params);if(U(aw)){ao=false}ak.push(aw);am=null;if(view.reference_track&&al>view.canvas_manager.char_width_px){am=view.reference_track.data_manager.get_data(ah,aq.mode,av,view.reference_track.data_url_extra_params);if(U(am)){ao=false}}ak.push(am)}if(ao){q(aw,at.more_tile_data);this.tile_predraw_init();var ag=aq.view.canvas_manager.new_canvas(),ay=ah.get("start"),ae=ah.get("end"),az=0,ar=Math.ceil((ae-ay)*al)+this.left_offset,ap=0,af=[],ax;var ac=0;for(ax=0;ax<this.drawables.length;ax++,az+=2){aq=this.drawables[ax];aw=ak[az];var an=aq.mode;if(an==="Auto"){an=aq.get_mode(aw);aq.update_auto_mode(an)}af.push(an);ac=aq.get_canvas_height(aw,an,al,ar);if(ac>ap){ap=ac}}ag.width=ar;ag.height=(at.height?at.height:ap);az=0;var au=ag.getContext("2d");au.translate(this.left_offset,0);au.globalAlpha=0.5;au.globalCompositeOperation="source-over";for(ax=0;ax<this.drawables.length;ax++,az+=2){aq=this.drawables[ax];aw=ak[az];am=ak[az+1];aA=aq.draw_tile(aw,au,af[ax],av,ah,al,am)}this.tile_cache.set_elt(aB,aA);this.show_tile(aA,aj,al);return aA}var ai=$.Deferred(),aq=this;$.when.apply($,ak).then(function(){view.request_redraw(false,false,false,aq);ai.resolve()});return ai},show_group:function(){var af=new P(this.view,this.container,{name:this.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()},tile_predraw_init:function(){var af=Number.MAX_VALUE,ac=-af,ad;for(var ae=0;ae<this.drawables.length;ae++){ad=this.drawables[ae];if(ad instanceof h){if(ad.prefs.min_value<af){af=ad.prefs.min_value}if(ad.prefs.max_value>ac){ac=ad.prefs.max_value}}}for(var ae=0;ae<this.drawables.length;ae++){ad=this.drawables[ae];ad.prefs.min_value=af;ad.prefs.max_value=ac}},postdraw_actions:function(ae,ah,aj,ad){M.prototype.postdraw_actions.call(this,ae,ah,aj,ad);var ag=-1;for(var af=0;af<ae.length;af++){var ac=ae[af].html_elt.find("canvas").height();if(ac>ag){ag=ac}}for(var af=0;af<ae.length;af++){var ai=ae[af];if(ai.html_elt.find("canvas").height()!==ag){this.draw_helper(true,ai.index,ai.resolution,ai.html_elt.parent(),aj,{height:ag});ai.html_elt.remove()}}}});var B=function(ac){M.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});ac.reference_track=this;this.left_offset=200;this.visible_height_px=12;this.container_div.addClass("reference-track");this.content_div.css("background","none");this.content_div.css("min-height","0px");this.content_div.css("border","none");this.data_url=reference_url+"/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new x.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(B.prototype,r.prototype,M.prototype,{build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},can_draw:r.prototype.can_draw,draw_helper:function(ae,af,ac,ag,ah,ad){if(ah>this.view.canvas_manager.char_width_px){this.tiles_div.show();return M.prototype.draw_helper.call(this,ae,af,ac,ag,ah,ad)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(af,al,ag,ad,ai,am){var ae=this.data_manager.subset_entry(af,ai),ak=ae.data;var ac=al.canvas;al.font=al.canvas.manager.default_font;al.textAlign="center";for(var ah=0,aj=ak.length;ah<aj;ah++){al.fillStyle=this.view.get_base_color(ak[ah]);al.fillText(ak[ah],Math.floor(ah*am),10)}return new b(this,ai,ad,ac,ae)}});var h=function(ae,ad,af){var ac=this;this.display_modes=["Histogram","Line","Filled","Intensity"];this.mode="Histogram";M.call(this,ae,ad,af);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{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:32,hidden:true}],saved_values:af.prefs,onchange:function(){ac.set_name(ac.prefs.name);ac.vertical_range=ac.prefs.max_value-ac.prefs.min_value;ac.set_min_value(ac.prefs.min_value);ac.set_max_value(ac.prefs.max_value)}});this.prefs=this.config.values;this.visible_height_px=this.config.values.height;this.vertical_range=this.config.values.max_value-this.config.values.min_value};q(h.prototype,r.prototype,M.prototype,{on_resize:function(){this.request_draw(true)},set_min_value:function(ac){this.prefs.min_value=ac;$("#linetrack_"+this.dataset_id+"_minval").text(this.prefs.min_value);this.tile_cache.clear();this.request_draw()},set_max_value:function(ac){this.prefs.max_value=ac;$("#linetrack_"+this.dataset_id+"_maxval").text(this.prefs.max_value);this.tile_cache.clear();this.request_draw()},predraw_init:function(){var ac=this;ac.vertical_range=undefined;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.hda_ldda},function(ad){ac.container_div.addClass("line-track");var ag=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=ag.min,ai=ag.max;ae=Math.floor(Math.min(0,Math.max(ae,ag.mean-2*ag.sd)));ai=Math.ceil(Math.max(0,Math.min(ai,ag.mean+2*ag.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ai;$("#track_"+ac.dataset_id+"_minval").val(ac.prefs.min_value);$("#track_"+ac.dataset_id+"_maxval").val(ac.prefs.max_value)}ac.vertical_range=ac.prefs.max_value-ac.prefs.min_value;ac.total_frequency=ag.total_frequency;ac.container_div.find(".yaxislabel").remove();var ah=$("<div/>").text(V(ac.prefs.min_value,3)).make_text_editable({num_cols:6,on_finish:function(aj){$(".bs-tooltip").remove();var aj=parseFloat(aj);if(!isNaN(aj)){ac.set_min_value(aj)}},help_text:"Set min value"}).addClass("yaxislabel bottom").attr("id","linetrack_"+ac.dataset_id+"_minval").prependTo(ac.container_div),af=$("<div/>").text(V(ac.prefs.max_value,3)).make_text_editable({num_cols:6,on_finish:function(aj){$(".bs-tooltip").remove();var aj=parseFloat(aj);if(!isNaN(aj)){ac.set_max_value(aj)}},help_text:"Set max value"}).addClass("yaxislabel top").attr("id","linetrack_"+ac.dataset_id+"_maxval").prependTo(ac.container_div)})},draw_tile:function(al,aj,ae,ad,ag,ak){var ac=aj.canvas,af=ag.get("start"),ai=ag.get("end"),ah=new L.LinePainter(al.data,af,ai,this.prefs,ae);ah.draw(aj,ac.width,ac.height,ak);return new b(this,ag,ad,ac,al.data)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)}});var t=function(ae,ad,af){var ac=this;this.display_modes=["Heatmap"];this.mode="Heatmap";M.call(this,ae,ad,af);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{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}],saved_values:af.prefs,onchange:function(){ac.set_name(ac.prefs.name);ac.vertical_range=ac.prefs.max_value-ac.prefs.min_value;ac.set_min_value(ac.prefs.min_value);ac.set_max_value(ac.prefs.max_value)}});this.prefs=this.config.values;this.visible_height_px=this.config.values.height;this.vertical_range=this.config.values.max_value-this.config.values.min_value};q(t.prototype,r.prototype,M.prototype,{on_resize:function(){this.request_draw(true)},set_min_value:function(ac){this.prefs.min_value=ac;this.tile_cache.clear();this.request_draw()},set_max_value:function(ac){this.prefs.max_value=ac;this.tile_cache.clear();this.request_draw()},draw_tile:function(ac,ae,ai,ag,ah,aj){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ah.get("start"),ah.get("end"),this.prefs,ai);ad.draw(ae,af.width,af.height,aj);return new b(this,ah,ag,af,ac.data)}});var c=function(af,ae,ah){var ad=this;this.display_modes=["Auto","Coverage","Dense","Squish","Pack"];M.call(this,af,ae,ah);var ag=l.get_random_color(),ac=l.get_random_color([ag,"#FFFFFF"]);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{key:"block_color",label:"Block color",type:"color",default_value:ag},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:ac},{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:"histogram_max",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:this.visible_height_px,hidden:true}],saved_values:ah.prefs,onchange:function(){ad.set_name(ad.prefs.name);ad.tile_cache.clear();ad.set_painter_from_config();ad.request_draw()}});this.prefs=this.config.values;this.visible_height_px=this.config.values.height;this.container_div.addClass("feature-track");this.show_labels_scale=0.001;this.showing_details=false;this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(c.prototype,r.prototype,M.prototype,{set_painter_from_config:function(){if(this.config.values.connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},before_draw:function(){this.max_height_px=0},postdraw_actions:function(ar,am,ah,ag){M.prototype.postdraw_actions.call(this,ar,ag);var al=this,ao;if(al.mode==="Coverage"){var ad=-1;for(ao=0;ao<ar.length;ao++){var an=ar[ao].max_val;if(an>ad){ad=an}}for(ao=0;ao<ar.length;ao++){var au=ar[ao];if(au.max_val!==ad){au.html_elt.remove();al.draw_helper(true,au.index,au.resolution,au.html_elt.parent(),ah,{more_tile_data:{max:ad}})}}}if(al.filters_manager){var ai=al.filters_manager.filters;for(var aq=0;aq<ai.length;aq++){ai[aq].update_ui_elt()}var at=false,ac,aj;for(ao=0;ao<ar.length;ao++){if(ar[ao].data.length){ac=ar[ao].data[0];for(var aq=0;aq<ai.length;aq++){aj=ai[aq];if(aj.applies_to(ac)&&aj.min!==aj.max){at=true;break}}}}if(al.filters_available!==at){al.filters_available=at;if(!al.filters_available){al.filters_manager.hide()}al.update_icons()}}this.container_div.find(".yaxislabel").remove();var af=ar[0];if(af instanceof j){var ak=(this.prefs.histogram_max?this.prefs.histogram_max:af.max_val),ae=$("<div/>").text(ak).make_text_editable({num_cols:12,on_finish:function(av){$(".bs-tooltip").remove();var av=parseFloat(av);al.prefs.histogram_max=(!isNaN(av)?av:null);al.tile_cache.clear();al.request_draw()},help_text:"Set max value; leave blank to use default"}).addClass("yaxislabel top").css("color",this.prefs.label_color);this.container_div.prepend(ae)}if(af instanceof O){var ap=true;for(ao=0;ao<ar.length;ao++){if(!ar[ao].all_slotted){ap=false;break}}if(!ap){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){var ac;if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}else{if(ac==="summary_tree"){ac="coverage histogram"}}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,A,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.dataset_type==="summary_tree"){mode="summary_tree"}else{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==="summary_tree"||ag==="Coverage"){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(aa,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,ar,af,aj,ae){var ap=this,ad=aq.canvas,ay=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(ao==="summary_tree"||ao==="Coverage"){return this._draw_summary_tree_tile(am,aq,af,ar,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var at=0,av=am.data.length;at<av;at++){var ah=am.data[at];var au=false;var al;for(var ax=0,aC=ak.length;ax<aC;ax++){al=ak[ax];al.update_attrs(ah);if(!al.keep(ah)){au=true;break}}if(!au){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aB=(this.filters_manager.alpha_filter?new C(this.filters_manager.alpha_filter):null),az=(this.filters_manager.height_filter?new C(this.filters_manager.height_filter):null),aA=new (this.painter)(ai,ay,ac,this.prefs,ao,aB,az,ae,function(aD){return ap.view.get_base_color(aD)});var aw=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){aw=aA.draw(aq,ad.width,ad.height,aj,an);aw.translation=-ag}return new O(ap,af,ar,ad,am.data,aj,ao,am.message,all_slotted,aw)},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="summary_tree"}else{if(ac.extra_info==="no_detail"||ac.dataset_type==="summary_tree"){return false}else{return true}}}},can_subset:function(ac){if(ac.dataset_type==="summary_tree"||ac.message||ac.extra_info==="no_detail"){return false}return true}});var Z=function(ad,ac,ae){this.display_modes=["Auto","Coverage","Dense","Squish","Pack"];M.call(this,ad,ac,ae);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{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}],saved_values:ae.prefs,onchange:function(){this.track.set_name(this.track.prefs.name);this.track.tile_cache.clear();this.track.request_draw()}});this.prefs=this.config.values;this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,M.prototype,{draw_tile:function(ac,af,ai,ag,ah,aj){if(ac.dataset_type==="summary_tree"){return this._draw_summary_tree_tile(ac,af,ah,ag,aj)}else{var ae=this.view,ad=new (this.painter)(ac.data,ah.get("start"),ah.get("end"),this.prefs,ai,function(ak){return ae.get_base_color(ak)});ad.draw(af,af.canvas.width,af.canvas.height,aj);return new b(this,ah,ag,af.canvas,ac.data)}},get_canvas_height:function(ac,af,ag,ad){if(ac.dataset_type==="summary_tree"){return this.summary_draw_height}else{var ae=new (this.painter)(ac.data,null,null,this.prefs,af);return ae.get_required_height()}},before_draw:function(){this.max_height_px=0},postdraw_actions:function(ai,ad,ak,ag){M.prototype.postdraw_actions.call(this,ai,ad,ak,ag);if(this.prefs.show_labels){if(this.container_div.find(".yaxislabel").length===0){var ac=10,aj=$("<div/>").text("Summary").addClass("yaxislabel top").css({"font-size":ac+"px"});this.container_div.prepend(aj);var ah=aj.position().top;aj.css("top",ah+(this.prefs.summary_height-ac)/2+"px");if(this.prefs.show_sample_data){var ae="";ab.each(this.dataset.get("metadata").get("sample_names"),function(al){ae+=(al+"<br>")});var af=$("<div/>").html(ae).addClass("yaxislabel top sample").css({top:ah+this.prefs.summary_height+2,});this.container_div.prepend(af)}}$(this.container_div).find(".sample").css("font-size",(this.mode==="Squish"?5:10)+"px");$(this.container_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel").remove()}}});var S=function(ae,ad,ag){c.call(this,ae,ad,ag);var af=l.get_random_color(),ac=l.get_random_color([af,"#ffffff"]);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{key:"block_color",label:"Block and sense strand color",type:"color",default_value:af},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:ac},{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:"histogram_max",label:"Histogram maximum",type:"float",default_value:null,help:"Clear value to set automatically"},{key:"mode",type:"string",default_value:this.mode,hidden:true}],saved_values:ag.prefs,onchange:function(){this.track.set_name(this.track.prefs.name);this.track.tile_cache.clear();this.track.request_draw()}});this.prefs=this.config.values;this.painter=(ae.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(S.prototype,r.prototype,M.prototype,c.prototype);var d={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:c,LineTrack:h,ReadTrack:S,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 d[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:c,DiagonalHeatmapTrack:t,ReadTrack:S,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","mvc/data","viz/trackster/filters"],function(ab,x,l,u,L,X,i){var q=ab.extend;var U=function(ac){return("isResolved" in ac)};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();if(ap.offsetY<aq){$(this).insertBefore(ai);var ar=n[ai.attr("id")];ar.remove_drawable(am);ar.container.add_drawable_before(am,ar);return}else{if(ap.offsetY>ah){$(this).insertAfter(ai);var ar=n[ai.attr("id")];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 aa=16,G=9,D=20,A=100,I=12000,R=400,K=5000,w=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.",E="No data for this chrom/contig.",v="Preparing data. This can take a while for a large dataset. If the visualization is saved and closed, preparation will continue in the background.",y="Tool cannot be rerun: ",a="Loading data...",T="Ready for display",Q=10,H=20;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.name=af.name;this.view=ad;this.container=ac;this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name}],saved_values:af.prefs,onchange:function(){this.track.set_name(this.track.config.values.name)}});this.prefs=this.config.values;this.drag_handle_class=af.drag_handle_class;this.is_overview=false;this.action_icons={};this.content_visible=true;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.content_visible){ac.action_icons.toggle_icon.addClass("toggle-expand").removeClass("toggle");ac.hide_contents();ac.content_visible=false}else{ac.action_icons.toggle_icon.addClass("toggle").removeClass("toggle-expand");ac.content_visible=true;ac.show_contents()}}},{name:"settings_icon",title:"Edit settings",css_class:"settings-icon",on_click_fn:function(ad){var af=function(){hide_modal();$(window).unbind("keypress.check_enter_esc")},ac=function(){ad.config.update_from_form($(".dialog-box"));hide_modal();$(window).unbind("keypress.check_enter_esc")},ae=function(ag){if((ag.keyCode||ag.which)===27){af()}else{if((ag.keyCode||ag.which)===13){ac()}}};$(window).bind("keypress.check_enter_esc",ae);show_modal("Configure",ad.config.build_form(),{Cancel:af,OK:ac})}},{name:"remove_icon",title:"Remove",css_class:"remove-icon",on_click_fn:function(ac){$(".bs-tooltip").remove();ac.remove()}}];q(r.prototype,{init:function(){},changed:function(){this.view.changed()},can_draw:function(){if(this.enabled&&this.content_visible){return true}return false},request_draw:function(){},_draw:function(){},to_dict:function(){},set_name:function(ac){this.old_name=this.name;this.name=ac;this.name_div.text(this.name)},revert_name:function(){if(this.old_name){this.name=this.old_name;this.name_div.text(this.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("href","javascript:void(0);").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 z=function(ad,ac,ae){r.call(this,ad,ac,ae);this.obj_type=ae.obj_type;this.drawables=[]};q(z.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(){for(var ac=0;ac<this.drawables.length;ac++){this.drawables[ac]._draw()}},to_dict:function(){var ad=[];for(var ac=0;ac<this.drawables.length;ac++){ad.push(this.drawables[ac].to_dict())}return{name:this.name,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}});var P=function(ad,ac,af){q(af,{obj_type:"DrawableGroup",drag_handle_class:"group-handle"});z.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,z.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){$(".bs-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(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.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 c){ac++}}if(ao||ac===1){this.action_icons.composite_icon.show()}else{this.action_icons.composite_icon.hide();$(".bs-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 af=[];for(var ad=0;ad<this.drawables.length;ad++){af.push(this.drawables[ad].name)}var ae=new f(this.view,this.view,{name:this.name,drawables:this.drawables});var ac=this.container.replace_drawable(this,ae,true);ae.request_draw()},add_drawable:function(ac){z.prototype.add_drawable.call(this,ac);this.update_icons()},remove_drawable:function(ac){z.prototype.remove_drawable.call(this,ac);this.update_icons()},to_dict:function(){if(this.filters_manager.visible()){this._restore_filter_managers()}var ac=q(z.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,ae){for(var ad=0;ad<this.drawables.length;ad++){this.drawables[ad].request_draw(ac,ae)}}});var Y=Backbone.View.extend({initialize:function(ac){q(ac,{obj_type:"View"});z.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 x.CanvasManager(this.container.get(0).ownerDocument);this.reset();this.config=new F({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(false,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(){x.select_datasets(select_datasets_url,add_track_async_url,{"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("href","javascript:void(0);").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_drawables(),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.values[ac.toLowerCase()+"_color"]||this.config.values.n_color}});q(Y.prototype,z.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=w;var ac=this,ad=$.Deferred();$.ajax({url:chrom_url+"/"+this.dbkey,data:ae,dataType:"json",success:function(ag){if(ag.chrom_info.length===0){return}if(ag.reference){ac.add_label_track(new B(ac))}ac.chrom_data=ag.chrom_info;var aj='<option value="">Select Chrom/Contig</option>';for(var ai=0,af=ac.chrom_data.length;ai<af;ai++){var ah=ac.chrom_data[ai].chrom;aj+='<option value="'+ah+'">'+ah+"</option>"}if(ag.prev_chroms){aj+='<option value="previous">Previous '+w+"</option>"}if(ag.next_chroms){aj+='<option value="next">Next '+w+"</option>"}ac.chrom_select.html(aj);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-w});return}if(ah==="next"){ae.load_chroms({low:this.chrom_start_index+w});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();ae.request_redraw(true);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();var ad=ac.chrom_select.val();this.trigger_navigate(ad,ac.low,ac.high,true)},add_drawable:function(ac){z.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){z.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(ak,ac,aj,al){var ai=this,ah=(al?[al]:ai.drawables),ae;var ad;for(var ag=0;ag<ah.length;ag++){ad=ah[ag];ae=-1;for(var af=0;af<ai.tracks_to_be_redrawn.length;af++){if(ai.tracks_to_be_redrawn[af][0]===ad){ae=af;break}}if(ae<0){ai.tracks_to_be_redrawn.push([ad,ac,aj])}else{ai.tracks_to_be_redrawn[ag][1]=ac;ai.tracks_to_be_redrawn[ag][2]=aj}}if(!this.requested_redraw){requestAnimationFrame(function(){ai._redraw(ak)});this.requested_redraw=true}},_redraw:function(am){this.requested_redraw=false;var aj=this.low,af=this.high;if(aj<this.max_low){aj=this.max_low}if(af>this.max_high){af=this.max_high}var al=this.high-this.low;if(this.high!==0&&al<this.min_separation){af=aj+this.min_separation}this.low=Math.floor(aj);this.high=Math.ceil(af);this.update_location(this.low,this.high);this.resolution_b_px=(this.high-this.low)/this.viewport_container.width();this.resolution_px_b=1/this.resolution_b_px;var ac=(this.low/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var ai=((this.high-this.low)/(this.max_high-this.max_low)*this.overview_viewport.width())||0;var an=13;this.overview_box.css({left:ac,width:Math.max(an,ai)}).show();if(ai<an){this.overview_box.css("left",ac-(an-ai)/2)}if(this.overview_highlight){this.overview_highlight.css({left:ac,width:ai})}if(!am){var ae,ad,ak;for(var ag=0,ah=this.tracks_to_be_redrawn.length;ag<ah;ag++){ae=this.tracks_to_be_redrawn[ag][0];ad=this.tracks_to_be_redrawn[ag][1];ak=this.tracks_to_be_redrawn[ag][2];if(ae){ae._draw(ad,ak)}}this.tracks_to_be_redrawn=[];for(ag=0,ah=this.label_tracks.length;ag<ah;ag++){this.label_tracks[ag]._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(){$(".bs-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=function(ae,aj,af){this.track=ae;this.id=aj.id;this.name=aj.name;this.params=[];var aq=aj.params;for(var ag=0;ag<aq.length;ag++){var al=aq[ag],ad=al.name,ap=al.label,ah=unescape(al.html),ar=al.value,an=al.type;if(an==="number"){this.params.push(new e(ad,ap,ah,(ad in af?af[ad]:ar),al.min,al.max))}else{if(an==="select"){this.params.push(new N(ad,ap,ah,(ad in af?af[ad]:ar)))}else{console.log("WARNING: unrecognized tool parameter type:",ad,an)}}}this.parent_div=$("<div/>").addClass("dynamic-tool").hide();this.parent_div.bind("drag",function(au){au.stopPropagation()}).click(function(au){au.stopPropagation()}).bind("dblclick",function(au){au.stopPropagation()});var ao=$("<div class='tool-name'>").appendTo(this.parent_div).text(this.name);var am=this.params;var ak=this;$.each(this.params,function(av,ay){var ax=$("<div>").addClass("param-row").appendTo(ak.parent_div);var au=$("<div>").addClass("param-label").text(ay.label).appendTo(ax);var aw=$("<div/>").addClass("param-input").html(ay.html).appendTo(ax);aw.find(":input").val(ay.value);$("<div style='clear: both;'/>").appendTo(ax)});this.parent_div.find("input").click(function(){$(this).select()});var at=$("<div>").addClass("param-row").appendTo(this.parent_div);var ai=$("<input type='submit'>").attr("value","Run on complete dataset").appendTo(at);var ac=$("<input type='submit'>").attr("value","Run on visible region").css("margin-left","3em").appendTo(at);ac.click(function(){ak.run_on_region()});ai.click(function(){ak.run_on_dataset()});if("visible" in af&&af.visible){this.parent_div.show()}};q(s.prototype,{update_params:function(){for(var ac=0;ac<this.params.length;ac++){this.params[ac].update_value()}},state_dict:function(){var ad={};for(var ac=0;ac<this.params.length;ac++){ad[this.params[ac].name]=this.params[ac].value}ad.visible=this.parent_div.is(":visible");return ad},get_param_values_dict:function(){var ac={};this.parent_div.find(":input").each(function(){var ad=$(this).attr("name"),ae=$(this).val();ac[ad]=ae});return ac},get_param_values:function(){var ac=[];this.parent_div.find(":input").each(function(){var ad=$(this).attr("name"),ae=$(this).val();if(ad){ac[ac.length]=ae}});return ac},run_on_dataset:function(){var ac=this;ac.run({target_dataset_id:this.track.dataset_id,action:"rerun",tool_id:ac.id},null,function(ad){show_modal(ac.name+" is Running",ac.name+" is running on the complete dataset. Tool outputs are in dataset's history.",{Close:hide_modal})})},run_on_region:function(){var ai=new x.GenomeRegion({chrom:this.track.view.chrom,start:this.track.view.low,end:this.track.view.high}),ad={target_dataset_id:this.track.dataset_id,action:"rerun",tool_id:this.id,regions:[ai.toJSON()]},ah=this.track,ae=ad.tool_id+ah.tool_region_and_parameters_str(ai),ac;if(ah.container===view){var ag=new P(view,view,{name:this.name});var af=ah.container.replace_drawable(ah,ag,false);ag.container_div.insertBefore(ah.view.content_div.children()[af]);ag.add_drawable(ah);ah.container_div.appendTo(ag.content_div);ac=ag}else{ac=ah.container}var aj=new ah.constructor(view,ac,{name:ae,hda_ldda:"hda"});aj.init_for_tool_data();aj.change_mode(ah.mode);aj.set_filters_manager(ah.filters_manager.copy(aj));aj.update_icons();ac.add_drawable(aj);aj.tiles_div.text("Starting job.");this.update_params();this.run(ad,aj,function(ak){aj.set_dataset(new X.Dataset(ak));aj.tiles_div.text("Running job.");aj.init()})},run:function(ac,ae,af){ac.inputs=this.get_param_values_dict();var ad=new l.ServerStateDeferred({ajax_settings:{url:galaxy_paths.get("tool_url"),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(y+ag.message)}else{af(ag)}}})}});var N=function(ad,ac,ae,af){this.name=ad;this.label=ac;this.html=$(ae);this.value=af};q(N.prototype,{update_value:function(){this.value=$(this.html).val()}});var e=function(ae,ad,ag,ah,af,ac){N.call(this,ae,ad,ag,ah);this.min=af;this.max=ac};q(e.prototype,N.prototype,{update_value:function(){N.prototype.update_value.call(this);this.value=parseFloat(this.value)}});var C=function(ac,ad){L.Scaler.call(this,ad);this.filter=ac};C.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 F=function(ac){this.track=ac.track;this.params=ac.params;this.values={};this.restore_values((ac.saved_values?ac.saved_values:{}));this.onchange=ac.onchange};q(F.prototype,{restore_values:function(ac){var ad=this;$.each(this.params,function(ae,af){if(ac[af.key]!==undefined){ad.values[af.key]=ac[af.key]}else{ad.values[af.key]=af.default_value}})},build_form:function(){var af=this;var ac=$("<div />");var ae;function ad(ak,ag){for(var ao=0;ao<ak.length;ao++){ae=ak[ao];if(ae.hidden){continue}var ai="param_"+ao;var at=af.values[ae.key];var av=$("<div class='form-row' />").appendTo(ag);av.append($("<label />").attr("for",ai).text(ae.label+":"));if(ae.type==="bool"){av.append($('<input type="checkbox" />').attr("id",ai).attr("name",ai).attr("checked",at))}else{if(ae.type==="text"){av.append($('<input type="text"/>').attr("id",ai).val(at).click(function(){$(this).select()}))}else{if(ae.type==="select"){var aq=$("<select />").attr("id",ai);for(var am=0;am<ae.options.length;am++){$("<option/>").text(ae.options[am].label).attr("value",ae.options[am].value).appendTo(aq)}aq.val(at);av.append(aq)}else{if(ae.type==="color"){var au=$("<div/>").appendTo(av),ap=$("<input />").attr("id",ai).attr("name",ai).val(at).css("float","left").appendTo(au).click(function(ax){$(".bs-tooltip").removeClass("in");var aw=$(this).siblings(".bs-tooltip").addClass("in");aw.css({left:$(this).position().left+$(this).width()+5,top:$(this).position().top-($(aw).height()/2)+($(this).height()/2)}).show();aw.click(function(ay){ay.stopPropagation()});$(document).bind("click.color-picker",function(){aw.hide();$(document).unbind("click.color-picker")});ax.stopPropagation()}),an=$("<a href='javascript:void(0)'/>").addClass("icon-button arrow-circle").appendTo(au).attr("title","Set new random color").tooltip(),ar=$("<div class='bs-tooltip right' style='position: absolute;' />").appendTo(au).hide(),aj=$("<div class='tooltip-inner' style='text-align: inherit'></div>").appendTo(ar),ah=$("<div class='tooltip-arrow'></div>").appendTo(ar),al=$.farbtastic(aj,{width:100,height:100,callback:ap,color:at});au.append($("<div/>").css("clear","both"));(function(aw){an.click(function(){aw.setColor(l.get_random_color())})})(al)}else{av.append($("<input />").attr("id",ai).attr("name",ai).val(at))}}}}if(ae.help){av.append($("<div class='help'/>").text(ae.help))}}}ad(this.params,ac);return ac},update_from_form:function(ac){var ae=this;var ad=false;$.each(this.params,function(af,ah){if(!ah.hidden){var ai="param_"+af;var ag=ac.find("#"+ai).val();if(ah.type==="float"){ag=parseFloat(ag)}else{if(ah.type==="int"){ag=parseInt(ag,10)}else{if(ah.type==="bool"){ag=ac.find("#"+ai).is(":checked")}}}if(ag!==ae.values[ah.key]){ae.values[ah.key]=ag;ad=true}}});if(ad){this.onchange();this.track.changed()}}});var b=function(ac,ag,ae,ad,af){this.track=ac;this.region=ag;this.low=ag.get("start");this.high=ag.get("end");this.resolution=ae;this.html_elt=$("<div class='track-tile'/>").append(ad).height($(ad).attr("height"));this.data=af;this.stale=false};b.prototype.predisplay_actions=function(){};var j=function(ac,ah,ae,ad,af,ag){b.call(this,ac,ah,ae,ad,af);this.max_val=ag};q(j.prototype,b.prototype);var O=function(af,an,ag,ae,ai,ap,aj,aq,ad,am){b.call(this,af,an,ag,ae,ai);this.mode=aj;this.all_slotted=ad;this.feature_mapper=am;this.has_icons=false;if(aq){this.has_icons=true;var ak=this;ae=this.html_elt.children()[0],message_div=$("<div/>").addClass("tile-message").css({height:D-1,width:ae.width}).prependTo(this.html_elt);var al=new x.GenomeRegion({chrom:af.view.chrom,start:this.low,end:this.high}),ao=ai.length,ah=$("<a href='javascript:void(0);'/>").addClass("icon more-down").attr("title","For speed, only the first "+ao+" features in this region were obtained from server. Click to get more data including depth").tooltip().appendTo(message_div),ac=$("<a href='javascript:void(0);'/>").addClass("icon more-across").attr("title","For speed, only the first "+ao+" features in this region were obtained from server. Click to get more data excluding depth").tooltip().appendTo(message_div);ah.click(function(){ak.stale=true;af.data_manager.get_more_data(al,af.mode,ak.resolution,{},af.data_manager.DEEP_DATA_REQ);$(".bs-tooltip").hide();af.request_draw(true)}).dblclick(function(ar){ar.stopPropagation()});ac.click(function(){ak.stale=true;af.data_manager.get_more_data(al,af.mode,ak.resolution,{},af.data_manager.BROAD_DATA_REQ);$(".bs-tooltip").hide();af.request_draw(true)}).dblclick(function(ar){ar.stopPropagation()})}};q(O.prototype,b.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 ak=at[0],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]}var af=$("<div/>").attr("id",ak).addClass("feature-popup"),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"))-af.width()/2,ae=am+parseInt(ad.html_elt.css("top"))+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=new X.Dataset(ae.dataset);this.dataset_id=this.dataset.get("id");this.hda_ldda=this.dataset.get("hda_ldda");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 x.GenomeDataManager({dataset:this.dataset,genome:new x.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=0;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.dynamic_tool_div.toggle();if(ac.dynamic_tool_div.is(":visible")){ac.set_name(ac.name+ac.tool_region_and_parameters_str())}else{ac.revert_name()}$(".bs-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(){hide_modal();$(window).unbind("keypress.check_enter_esc")},ad=function(){var aj=$('select[name="regions"] option:selected').val(),al,ai=new x.GenomeRegion({chrom:view.chrom,start:view.low,end:view.high}),ak=ab.map($(".bookmark"),function(am){return new x.GenomeRegion({from_str:$(am).children(".position").text()})});if(aj==="cur"){al=[ai]}else{if(aj==="bookmarks"){al=ak}else{al=[ai].concat(ak)}}hide_modal();window.location.href=galaxy_paths.get("sweepster_url")+"?"+$.param({dataset_id:ac.dataset_id,hda_ldda:ac.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()}}};show_modal("Visualize tool parameter space and output from different parameter settings?",ae,{No:ah,Yes:ad})}},r.prototype.action_icons_def[2]],can_draw:function(){if(this.dataset_id&&r.prototype.can_draw.call(this)){return true}return false},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.name).attr("id",this.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);this.dataset_id=ac.get("id");this.hda_ldda=ac.get("hda_ldda")},on_resize:function(){},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.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.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.values.mode?this.config.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 B){return"ReferenceTrack"}else{if(this instanceof h){return"LineTrack"}else{if(this instanceof S){return"ReadTrack"}else{if(this instanceof Z){return"VariantTrack"}else{if(this instanceof f){return"CompositeTrack"}else{if(this instanceof c){return"FeatureTrack"}}}}}}}return""},init:function(ae){var ad=this;ad.enabled=false;ad.tile_cache.clear();ad.data_manager.clear();ad.content_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.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(){show_modal("Trackster Error","<pre>"+ag.message+"</pre>",{Close:hide_modal})}));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(E)}else{if(ag==="pending"){ad.container_div.addClass("pending");ad.tiles_div.html(v);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(T);if(ad.view.chrom){ad.tiles_div.text("");ad.tiles_div.css("height",ad.visible_height_px+"px");ad.enabled=true;$.when(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(){},get_drawables:function(){return this}});var M=function(ae,ad,af){g.call(this,ae,ad,af);var ac=this;m(ac.container_div,ac.drag_handle_class,".group",ac);this.filters_manager=new i.FiltersManager(this,("filters" in af?af.filters:null));this.data_manager.set("filters_manager",this.filters_manager);this.filters_available=false;this.tool=("tool" in af&&af.tool?new s(this,af.tool,af.tool_state):null);this.tile_cache=new x.Cache(Q);this.left_offset=0;if(this.header_div){this.set_filters_manager(this.filters_manager);if(this.tool){this.dynamic_tool_div=this.tool.parent_div;this.header_div.after(this.dynamic_tool_div)}}this.tiles_div=$("<div/>").addClass("tiles").appendTo(this.content_div);this.overlay_div=$("<div/>").addClass("overlay").appendTo(this.content_div);if(af.mode){this.change_mode(af.mode)}};q(M.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){$(".bs-tooltip").remove();ac.slotters[ac.view.resolution_px_b].max_rows*=2;ac.request_draw(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(),name:this.name,hda_ldda:this.hda_ldda,dataset_id:this.dataset_id,prefs:this.prefs,mode:this.mode,filters:this.filters_manager.to_dict(),tool_state:(this.tool?this.tool.state_dict():{})}},change_mode:function(ad){var ac=this;ac.mode=ad;ac.config.values.mode=ad;ac.tile_cache.clear();ac.request_draw();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(ad,ac){this.view.request_redraw(false,ad,ac,this)},before_draw:function(){},_draw:function(ad,ao){if(!this.can_draw()){return}var al=this.view.low,ah=this.view.high,aj=ah-al,ae=this.view.container.width(),aq=this.view.resolution_px_b,ag=this.view.resolution_b_px;if(this.is_overview){al=this.view.max_low;ah=this.view.max_high;ag=(view.max_high-view.max_low)/ae;aq=1/ag}this.before_draw();this.tiles_div.children().addClass("remove");var ac=Math.floor(al/(ag*R)),ak=true,ap=[],ai=function(ar){return(ar&&"track" in ar)};while((ac*R*ag)<ah){var am=this._get_tile_bounds(ac,ag),an=this.draw_helper(ad,am,ag,this.tiles_div,aq);if(ai(an)){ap.push(an)}else{ak=false}ac+=1}if(!ao){this.tiles_div.children(".remove").removeClass("remove").remove()}var af=this;if(ak){this.tiles_div.children(".remove").remove();af.postdraw_actions(ap,ae,aq,ao)}},postdraw_actions:function(ad,ae,ag,ac){var af=ab.find(ad,function(ah){return ah.has_icons});if(af){ab.each(ad,function(ah){if(!ah.has_icons){ah.html_elt.css("padding-top",D)}})}},draw_helper:function(ac,af,ar,ah,ai,ao){var an=this,aw=this._gen_tile_cache_key(ai,af);if(!ao){ao={}}var av=(ac?undefined:an.tile_cache.get_elt(aw));if(av){an.show_tile(av,ah,ai);return av}var al=true;var at=an.data_manager.get_data(af,an.mode,ar,an.data_url_extra_params);if(U(at)){al=false}var aj;if(view.reference_track){aj=view.reference_track.data_manager.get_data(af,an.mode,ar,view.reference_track.data_url_extra_params);if(U(aj)){al=false}else{aj=view.reference_track.data_manager.subset_entry(aj,af)}}if(al){q(at,ao.more_tile_data);var ak=an.mode;if(ak==="Auto"&&an.get_mode){ak=an.get_mode(at);an.update_auto_mode(ak)}var ae=an.view.canvas_manager.new_canvas(),au=af.get("start"),ad=af.get("end"),ap=Math.ceil((ad-au)*ai)+an.left_offset,am=an.get_canvas_height(at,ak,ai,ap);ae.width=ap;ae.height=am;var aq=ae.getContext("2d");aq.translate(this.left_offset,0);var av=an.draw_tile(at,aq,ak,ar,af,ai,aj);if(av!==undefined){an.tile_cache.set_elt(aw,av);an.show_tile(av,ah,ai)}return av}var ag=$.Deferred();$.when(at,aj).then(function(){view.request_redraw(false,false,false,an);ag.resolve()});return ag},get_canvas_height:function(ac,ae,af,ad){return this.visible_height_px},_draw_summary_tree_tile:function(ac,ae,ag,af,ah){var ad=new L.SummaryTreePainter(ac,ag.get("start"),ag.get("end"),this.prefs);ad.draw(ae,ae.canvas.width,ae.canvas.height,ah);return new j(this,ag,af,ae.canvas,ac.data,ac.max)},draw_tile:function(ac,ad,ah,af,ag,ai,ae){console.log("Warning: TiledTrack.draw_tile() not implemented.")},show_tile:function(ae,ah,ai){var ad=this,ac=ae.html_elt;ae.predisplay_actions();var ag=(ae.low-(this.is_overview?this.view.max_low:this.view.low))*ai;if(this.left_offset){ag-=this.left_offset}ac.css({position:"absolute",top:0,left:ag});if(ac.hasClass("remove")){ac.removeClass("remove")}else{ah.append(ac)}ae.html_elt.height("auto");this.max_height_px=Math.max(this.max_height_px,ae.html_elt.height());ae.html_elt.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")},_get_tile_bounds:function(ac,ad){var af=Math.floor(ac*R*ad),ag=Math.ceil(R*ad),ae=(af+ag<=this.view.max_high?af+ag:this.view.max_high);return new x.GenomeRegion({chrom:this.view.chrom,start:af,end:ae})},tool_region_and_parameters_str:function(ae){var ac=this,ad=(ae!==undefined?ae.toString():"all");return" - region=["+ad+"], parameters=["+ac.tool.get_param_values().join(", ")+"]"},data_and_mode_compatible:function(ac,ad){return true},can_subset:function(ac){return false},init_for_tool_data:function(){this.data_manager.set("data_type","raw_data");this.data_query_wait=1000;this.dataset_check_type="state";this.normal_postdraw_actions=this.postdraw_actions;this.postdraw_actions=function(ae,af,ah,ac){var ad=this;ad.normal_postdraw_actions(ae,af,ah,ac);ad.dataset_check_type="converted_datasets_state";ad.data_query_wait=K;var ag=new l.ServerStateDeferred({url:ad.dataset_state_url,url_params:{dataset_id:ad.dataset_id,hda_ldda:ad.hda_ldda},interval:ad.data_query_wait,success_fn:function(ai){return ai!=="pending"}});$.when(ag.go()).then(function(){ad.data_manager.set("data_type","data")});ad.postdraw_actions=ad.normal_postdraw_actions}}});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},_draw:function(){var ae=this.view,af=ae.high-ae.low,ai=Math.floor(Math.pow(10,Math.floor(Math.log(af)/Math.log(10)))),ac=Math.floor(ae.low/ai)*ai,ag=this.view.container.width(),ad=$("<div style='position: relative; height: 1.3em;'></div>");while(ac<ae.high){var ah=(ac-ae.low)/af*ag;ad.append($("<div class='label'>"+commatize(ac)+"</div>").css({position:"absolute",left:ah-1}));ac+=ai}this.content_div.children(":first").remove();this.content_div.append(ad)}});var f=function(ad,ac,ag){M.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}if(this.drawables.length!==0){this.set_display_modes(this.drawables[0].display_modes,this.drawables[0].mode)}this.update_icons();this.obj_type="CompositeTrack"};q(f.prototype,M.prototype,{action_icons_def:[{name:"composite_icon",title:"Show individual tracks",css_class:"layers-stack",on_click_fn:function(ac){$(".bs-tooltip").remove();ac.show_group()}}].concat(M.prototype.action_icons_def),to_dict:z.prototype.to_dict,add_drawable:z.prototype.add_drawable,unpack_drawables:z.prototype.unpack_drawables,change_mode:function(ac){M.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,draw_helper:function(ad,ah,av,aj,al,at){var aq=this,aB=this._gen_tile_cache_key(al,ah);if(!at){at={}}var aA=(ad?undefined:aq.tile_cache.get_elt(aB));if(aA){aq.show_tile(aA,aj,al);return aA}var ak=[],aq,ao=true,aw,am;for(var ax=0;ax<this.drawables.length;ax++){aq=this.drawables[ax];aw=aq.data_manager.get_data(ah,aq.mode,av,aq.data_url_extra_params);if(U(aw)){ao=false}ak.push(aw);am=null;if(view.reference_track&&al>view.canvas_manager.char_width_px){am=view.reference_track.data_manager.get_data(ah,aq.mode,av,view.reference_track.data_url_extra_params);if(U(am)){ao=false}}ak.push(am)}if(ao){q(aw,at.more_tile_data);this.tile_predraw_init();var ag=aq.view.canvas_manager.new_canvas(),ay=ah.get("start"),ae=ah.get("end"),az=0,ar=Math.ceil((ae-ay)*al)+this.left_offset,ap=0,af=[],ax;var ac=0;for(ax=0;ax<this.drawables.length;ax++,az+=2){aq=this.drawables[ax];aw=ak[az];var an=aq.mode;if(an==="Auto"){an=aq.get_mode(aw);aq.update_auto_mode(an)}af.push(an);ac=aq.get_canvas_height(aw,an,al,ar);if(ac>ap){ap=ac}}ag.width=ar;ag.height=(at.height?at.height:ap);az=0;var au=ag.getContext("2d");au.translate(this.left_offset,0);au.globalAlpha=0.5;au.globalCompositeOperation="source-over";for(ax=0;ax<this.drawables.length;ax++,az+=2){aq=this.drawables[ax];aw=ak[az];am=ak[az+1];aA=aq.draw_tile(aw,au,af[ax],av,ah,al,am)}this.tile_cache.set_elt(aB,aA);this.show_tile(aA,aj,al);return aA}var ai=$.Deferred(),aq=this;$.when.apply($,ak).then(function(){view.request_redraw(false,false,false,aq);ai.resolve()});return ai},show_group:function(){var af=new P(this.view,this.container,{name:this.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()},tile_predraw_init:function(){var af=Number.MAX_VALUE,ac=-af,ad;for(var ae=0;ae<this.drawables.length;ae++){ad=this.drawables[ae];if(ad instanceof h){if(ad.prefs.min_value<af){af=ad.prefs.min_value}if(ad.prefs.max_value>ac){ac=ad.prefs.max_value}}}for(var ae=0;ae<this.drawables.length;ae++){ad=this.drawables[ae];ad.prefs.min_value=af;ad.prefs.max_value=ac}},postdraw_actions:function(ae,ah,aj,ad){M.prototype.postdraw_actions.call(this,ae,ah,aj,ad);var ag=-1;for(var af=0;af<ae.length;af++){var ac=ae[af].html_elt.find("canvas").height();if(ac>ag){ag=ac}}for(var af=0;af<ae.length;af++){var ai=ae[af];if(ai.html_elt.find("canvas").height()!==ag){this.draw_helper(true,ai.index,ai.resolution,ai.html_elt.parent(),aj,{height:ag});ai.html_elt.remove()}}}});var B=function(ac){M.call(this,ac,{content_div:ac.top_labeltrack},{resize:false});ac.reference_track=this;this.left_offset=200;this.visible_height_px=12;this.container_div.addClass("reference-track");this.content_div.css("background","none");this.content_div.css("min-height","0px");this.content_div.css("border","none");this.data_url=reference_url+"/"+this.view.dbkey;this.data_url_extra_params={reference:true};this.data_manager=new x.GenomeReferenceDataManager({data_url:this.data_url,can_subset:this.can_subset});this.hide_contents()};q(B.prototype,r.prototype,M.prototype,{build_header_div:function(){},init:function(){this.data_manager.clear();this.enabled=true},can_draw:r.prototype.can_draw,draw_helper:function(ae,af,ac,ag,ah,ad){if(ah>this.view.canvas_manager.char_width_px){this.tiles_div.show();return M.prototype.draw_helper.call(this,ae,af,ac,ag,ah,ad)}else{this.tiles_div.hide();return null}},can_subset:function(ac){return true},draw_tile:function(af,al,ag,ad,ai,am){var ae=this.data_manager.subset_entry(af,ai),ak=ae.data;var ac=al.canvas;al.font=al.canvas.manager.default_font;al.textAlign="center";for(var ah=0,aj=ak.length;ah<aj;ah++){al.fillStyle=this.view.get_base_color(ak[ah]);al.fillText(ak[ah],Math.floor(ah*am),10)}return new b(this,ai,ad,ac,ae)}});var h=function(ae,ad,af){var ac=this;this.display_modes=["Histogram","Line","Filled","Intensity"];this.mode="Histogram";M.call(this,ae,ad,af);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{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:32,hidden:true}],saved_values:af.prefs,onchange:function(){ac.set_name(ac.prefs.name);ac.vertical_range=ac.prefs.max_value-ac.prefs.min_value;ac.set_min_value(ac.prefs.min_value);ac.set_max_value(ac.prefs.max_value)}});this.prefs=this.config.values;this.visible_height_px=this.config.values.height;this.vertical_range=this.config.values.max_value-this.config.values.min_value};q(h.prototype,r.prototype,M.prototype,{on_resize:function(){this.request_draw(true)},set_min_value:function(ac){this.prefs.min_value=ac;$("#linetrack_"+this.dataset_id+"_minval").text(this.prefs.min_value);this.tile_cache.clear();this.request_draw()},set_max_value:function(ac){this.prefs.max_value=ac;$("#linetrack_"+this.dataset_id+"_maxval").text(this.prefs.max_value);this.tile_cache.clear();this.request_draw()},predraw_init:function(){var ac=this;ac.vertical_range=undefined;return $.getJSON(ac.dataset.url(),{data_type:"data",stats:true,chrom:ac.view.chrom,low:0,high:ac.view.max_high,hda_ldda:ac.hda_ldda},function(ad){ac.container_div.addClass("line-track");var ag=ad.data;if(isNaN(parseFloat(ac.prefs.min_value))||isNaN(parseFloat(ac.prefs.max_value))){var ae=ag.min,ai=ag.max;ae=Math.floor(Math.min(0,Math.max(ae,ag.mean-2*ag.sd)));ai=Math.ceil(Math.max(0,Math.min(ai,ag.mean+2*ag.sd)));ac.prefs.min_value=ae;ac.prefs.max_value=ai;$("#track_"+ac.dataset_id+"_minval").val(ac.prefs.min_value);$("#track_"+ac.dataset_id+"_maxval").val(ac.prefs.max_value)}ac.vertical_range=ac.prefs.max_value-ac.prefs.min_value;ac.total_frequency=ag.total_frequency;ac.container_div.find(".yaxislabel").remove();var ah=$("<div/>").text(V(ac.prefs.min_value,3)).make_text_editable({num_cols:6,on_finish:function(aj){$(".bs-tooltip").remove();var aj=parseFloat(aj);if(!isNaN(aj)){ac.set_min_value(aj)}},help_text:"Set min value"}).addClass("yaxislabel bottom").attr("id","linetrack_"+ac.dataset_id+"_minval").prependTo(ac.container_div),af=$("<div/>").text(V(ac.prefs.max_value,3)).make_text_editable({num_cols:6,on_finish:function(aj){$(".bs-tooltip").remove();var aj=parseFloat(aj);if(!isNaN(aj)){ac.set_max_value(aj)}},help_text:"Set max value"}).addClass("yaxislabel top").attr("id","linetrack_"+ac.dataset_id+"_maxval").prependTo(ac.container_div)})},draw_tile:function(al,aj,ae,ad,ag,ak){var ac=aj.canvas,af=ag.get("start"),ai=ag.get("end"),ah=new L.LinePainter(al.data,af,ai,this.prefs,ae);ah.draw(aj,ac.width,ac.height,ak);return new b(this,ag,ad,ac,al.data)},can_subset:function(ac){return(ac.data[1][0]-ac.data[0][0]===1)}});var t=function(ae,ad,af){var ac=this;this.display_modes=["Heatmap"];this.mode="Heatmap";M.call(this,ae,ad,af);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{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}],saved_values:af.prefs,onchange:function(){ac.set_name(ac.prefs.name);ac.vertical_range=ac.prefs.max_value-ac.prefs.min_value;ac.set_min_value(ac.prefs.min_value);ac.set_max_value(ac.prefs.max_value)}});this.prefs=this.config.values;this.visible_height_px=this.config.values.height;this.vertical_range=this.config.values.max_value-this.config.values.min_value};q(t.prototype,r.prototype,M.prototype,{on_resize:function(){this.request_draw(true)},set_min_value:function(ac){this.prefs.min_value=ac;this.tile_cache.clear();this.request_draw()},set_max_value:function(ac){this.prefs.max_value=ac;this.tile_cache.clear();this.request_draw()},draw_tile:function(ac,ae,ai,ag,ah,aj){var af=ae.canvas,ad=new L.DiagonalHeatmapPainter(ac.data,ah.get("start"),ah.get("end"),this.prefs,ai);ad.draw(ae,af.width,af.height,aj);return new b(this,ah,ag,af,ac.data)}});var c=function(af,ae,ah){var ad=this;this.display_modes=["Auto","Coverage","Dense","Squish","Pack"];M.call(this,af,ae,ah);var ag=l.get_random_color(),ac=l.get_random_color([ag,"#FFFFFF"]);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{key:"block_color",label:"Block color",type:"color",default_value:ag},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:ac},{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:"histogram_max",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:this.visible_height_px,hidden:true}],saved_values:ah.prefs,onchange:function(){ad.set_name(ad.prefs.name);ad.tile_cache.clear();ad.set_painter_from_config();ad.request_draw()}});this.prefs=this.config.values;this.visible_height_px=this.config.values.height;this.container_div.addClass("feature-track");this.show_labels_scale=0.001;this.showing_details=false;this.summary_draw_height=30;this.slotters={};this.start_end_dct={};this.left_offset=200;this.set_painter_from_config()};q(c.prototype,r.prototype,M.prototype,{set_painter_from_config:function(){if(this.config.values.connector_style==="arcs"){this.painter=L.ArcLinkedFeaturePainter}else{this.painter=L.LinkedFeaturePainter}},before_draw:function(){this.max_height_px=0},postdraw_actions:function(ar,am,ah,ag){M.prototype.postdraw_actions.call(this,ar,ag);var al=this,ao;if(al.mode==="Coverage"){var ad=-1;for(ao=0;ao<ar.length;ao++){var an=ar[ao].max_val;if(an>ad){ad=an}}for(ao=0;ao<ar.length;ao++){var au=ar[ao];if(au.max_val!==ad){au.html_elt.remove();al.draw_helper(true,au.index,au.resolution,au.html_elt.parent(),ah,{more_tile_data:{max:ad}})}}}if(al.filters_manager){var ai=al.filters_manager.filters;for(var aq=0;aq<ai.length;aq++){ai[aq].update_ui_elt()}var at=false,ac,aj;for(ao=0;ao<ar.length;ao++){if(ar[ao].data.length){ac=ar[ao].data[0];for(var aq=0;aq<ai.length;aq++){aj=ai[aq];if(aj.applies_to(ac)&&aj.min!==aj.max){at=true;break}}}}if(al.filters_available!==at){al.filters_available=at;if(!al.filters_available){al.filters_manager.hide()}al.update_icons()}}this.container_div.find(".yaxislabel").remove();var af=ar[0];if(af instanceof j){var ak=(this.prefs.histogram_max?this.prefs.histogram_max:af.max_val),ae=$("<div/>").text(ak).make_text_editable({num_cols:12,on_finish:function(av){$(".bs-tooltip").remove();var av=parseFloat(av);al.prefs.histogram_max=(!isNaN(av)?av:null);al.tile_cache.clear();al.request_draw()},help_text:"Set max value; leave blank to use default"}).addClass("yaxislabel top").css("color",this.prefs.label_color);this.container_div.prepend(ae)}if(af instanceof O){var ap=true;for(ao=0;ao<ar.length;ao++){if(!ar[ao].all_slotted){ap=false;break}}if(!ap){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){var ac;if(this.mode==="Auto"){if(ac==="no_detail"){ac="feature spans"}else{if(ac==="summary_tree"){ac="coverage histogram"}}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,A,function(ah){return ad.measureText(ah)});this.slotters[ag]=ae}return ae.slot_features(ac)},get_mode:function(ac){if(ac.dataset_type==="summary_tree"){mode="summary_tree"}else{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==="summary_tree"||ag==="Coverage"){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(aa,ae.get_required_height(af,ad))}},draw_tile:function(am,aq,ao,ar,af,aj,ae){var ap=this,ad=aq.canvas,ay=af.get("start"),ac=af.get("end"),ag=this.left_offset;if(ao==="summary_tree"||ao==="Coverage"){return this._draw_summary_tree_tile(am,aq,af,ar,aj)}var ai=[],an=this.slotters[aj].slots;all_slotted=true;if(am.data){var ak=this.filters_manager.filters;for(var at=0,av=am.data.length;at<av;at++){var ah=am.data[at];var au=false;var al;for(var ax=0,aC=ak.length;ax<aC;ax++){al=ak[ax];al.update_attrs(ah);if(!al.keep(ah)){au=true;break}}if(!au){ai.push(ah);if(!(ah[0] in an)){all_slotted=false}}}}var aB=(this.filters_manager.alpha_filter?new C(this.filters_manager.alpha_filter):null),az=(this.filters_manager.height_filter?new C(this.filters_manager.height_filter):null),aA=new (this.painter)(ai,ay,ac,this.prefs,ao,aB,az,ae,function(aD){return ap.view.get_base_color(aD)});var aw=null;aq.fillStyle=this.prefs.block_color;aq.font=aq.canvas.manager.default_font;aq.textAlign="right";if(am.data){aw=aA.draw(aq,ad.width,ad.height,aj,an);aw.translation=-ag}return new O(ap,af,ar,ad,am.data,aj,ao,am.message,all_slotted,aw)},data_and_mode_compatible:function(ac,ad){if(ad==="Auto"){return true}else{if(ad==="Coverage"){return ac.dataset_type==="summary_tree"}else{if(ac.extra_info==="no_detail"||ac.dataset_type==="summary_tree"){return false}else{return true}}}},can_subset:function(ac){if(ac.dataset_type==="summary_tree"||ac.message||ac.extra_info==="no_detail"){return false}return true}});var Z=function(ad,ac,ae){this.display_modes=["Auto","Coverage","Dense","Squish","Pack"];M.call(this,ad,ac,ae);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{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}],saved_values:ae.prefs,onchange:function(){this.track.set_name(this.track.prefs.name);this.track.tile_cache.clear();this.track.request_draw()}});this.prefs=this.config.values;this.painter=L.VariantPainter;this.summary_draw_height=30;this.left_offset=30};q(Z.prototype,r.prototype,M.prototype,{draw_tile:function(ac,af,ai,ag,ah,aj){if(ac.dataset_type==="summary_tree"){return this._draw_summary_tree_tile(ac,af,ah,ag,aj)}else{var ae=this.view,ad=new (this.painter)(ac.data,ah.get("start"),ah.get("end"),this.prefs,ai,function(ak){return ae.get_base_color(ak)});ad.draw(af,af.canvas.width,af.canvas.height,aj);return new b(this,ah,ag,af.canvas,ac.data)}},get_canvas_height:function(ac,af,ag,ad){if(ac.dataset_type==="summary_tree"){return this.summary_draw_height}else{var ae=new (this.painter)(ac.data,null,null,this.prefs,af);return ae.get_required_height()}},before_draw:function(){this.max_height_px=0},postdraw_actions:function(ai,ad,ak,ag){M.prototype.postdraw_actions.call(this,ai,ad,ak,ag);if(this.prefs.show_labels){if(this.container_div.find(".yaxislabel").length===0){var ac=10,aj=$("<div/>").text("Summary").addClass("yaxislabel top").css({"font-size":ac+"px"});this.container_div.prepend(aj);var ah=aj.position().top;aj.css("top",ah+(this.prefs.summary_height-ac)/2+"px");if(this.prefs.show_sample_data){var ae="";ab.each(this.dataset.get("metadata").get("sample_names"),function(al){ae+=(al+"<br>")});var af=$("<div/>").html(ae).addClass("yaxislabel top sample").css({top:ah+this.prefs.summary_height+2,});this.container_div.prepend(af)}}$(this.container_div).find(".sample").css("font-size",(this.mode==="Squish"?5:10)+"px");$(this.container_div).find(".yaxislabel").css("color",this.prefs.label_color)}else{this.container_div.find(".yaxislabel").remove()}}});var S=function(ae,ad,ag){c.call(this,ae,ad,ag);var af=l.get_random_color(),ac=l.get_random_color([af,"#ffffff"]);this.config=new F({track:this,params:[{key:"name",label:"Name",type:"text",default_value:this.name},{key:"block_color",label:"Block and sense strand color",type:"color",default_value:af},{key:"reverse_strand_color",label:"Antisense strand color",type:"color",default_value:ac},{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:"histogram_max",label:"Histogram maximum",type:"float",default_value:null,help:"Clear value to set automatically"},{key:"mode",type:"string",default_value:this.mode,hidden:true}],saved_values:ag.prefs,onchange:function(){this.track.set_name(this.track.prefs.name);this.track.tile_cache.clear();this.track.request_draw()}});this.prefs=this.config.values;this.painter=(ae.reference_track?L.RefBasedReadPainter:L.ReadPainter);this.update_icons()};q(S.prototype,r.prototype,M.prototype,c.prototype);var d={CompositeTrack:f,DrawableGroup:P,DiagonalHeatmapTrack:t,FeatureTrack:c,LineTrack:h,ReadTrack:S,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 d[af](ad,ac,ae)}};return{TracksterView:Y,DrawableGroup:P,LineTrack:h,FeatureTrack:c,DiagonalHeatmapTrack:t,ReadTrack:S,VariantTrack:Z,CompositeTrack:f,object_from_template:p}});
\ No newline at end of file
diff -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 -r 90e18fe3eb822d7b9380b554cd7464f083f0e931 static/scripts/viz/trackster/painters.js
--- a/static/scripts/viz/trackster/painters.js
+++ b/static/scripts/viz/trackster/painters.js
@@ -1577,7 +1577,14 @@
height += this.divider_height;
if (this.data.length !== 0) {
// Sample data is separated by commas, so this computes # of samples:
- height += (this.data[0][7].match(/,/g).length + 1) * this.get_row_height();
+ var comma_match = this.data[0][7].match(/,/g);
+ if ( comma_match === null ) {
+ comma_match = 1;
+ }
+ else {
+ comma_match = comma_match.length + 1;
+ }
+ height += ( comma_match * this.get_row_height() );
}
}
return height;
diff -r 8f0a3c34af315d5e5b47c6762a0241bca7c7df64 -r 90e18fe3eb822d7b9380b554cd7464f083f0e931 static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -1120,7 +1120,7 @@
},
get_base_color: function(base) {
- return this.config.values[ base.toLowerCase() + '_color' ];
+ return this.config.values[ base.toLowerCase() + '_color' ] || this.config.values[ 'n_color' ];
}
});
https://bitbucket.org/galaxy/galaxy-central/commits/93e4d0e6f1fe/
Changeset: 93e4d0e6f1fe
User: dannon
Date: 2013-04-22 15:19:54
Summary: Merge.
Affected #: 43 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/a456f964cef1/
Changeset: a456f964cef1
User: dannon
Date: 2013-04-29 19:09:15
Summary: Additional migration changes necessary to start w/ a clean sqlite database.
Affected #: 11 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/d4edf64c9a19/
Changeset: d4edf64c9a19
User: dannon
Date: 2013-04-29 19:23:44
Summary: Merge
Affected #: 66 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/ccc0c58e25f6/
Changeset: ccc0c58e25f6
User: dannon
Date: 2013-04-29 22:38:02
Summary: Drop cloud tables in order to avoid hacky cascade drop.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/3b7cd8cedca1/
Changeset: 3b7cd8cedca1
User: dannon
Date: 2013-04-30 15:32:19
Summary: History API: Import sanitize_html directly instead of using util reference
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/107e465405ff/
Changeset: 107e465405ff
User: dannon
Date: 2013-04-30 20:53:17
Summary: Migration script 0003, prevent sqlite from attempting to add a ForeignKey
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/b956501df7ee/
Changeset: b956501df7ee
User: dannon
Date: 2013-04-30 20:53:48
Summary: Migration script 0020, prevent sqlite from attempting to add a ForeignKey
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/6c28563c709f/
Changeset: 6c28563c709f
User: dannon
Date: 2013-04-30 20:55:04
Summary: Migration script 0036, 0038, use '0' as boolean for sqlite.
Affected #: 2 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/45682ff7f6e9/
Changeset: 45682ff7f6e9
User: dannon
Date: 2013-04-30 20:56:43
Summary: Sqlalchemy-migrate doesn't properly handle alter table add column w/ nullable=false in sqlite, skip constraint for dialect
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/6712944bc955/
Changeset: 6712944bc955
User: dannon
Date: 2013-04-30 20:57:56
Summary: Migration scripts 0037, 0068, 0073 -- skip foreign key creation for sqlite
Affected #: 3 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/0a3965f5953e/
Changeset: 0a3965f5953e
User: dannon
Date: 2013-04-30 20:58:06
Summary: merge
Affected #: 16 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/207271b8a75c/
Changeset: 207271b8a75c
User: dannon
Date: 2013-05-01 00:56:34
Summary: Update migration script 100 to use the new dialect name 'postgresql' -- still compatible with older versions too with 'postgres'.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/27328200c337/
Changeset: 27328200c337
User: dannon
Date: 2013-05-01 01:08:44
Summary: Remove assignmapper imports from migration 0080 -- it's gone now.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/2c0552e5e65d/
Changeset: 2c0552e5e65d
User: dannon
Date: 2013-05-01 01:09:17
Summary: Migration 0084 -- don't add ForeignKey for sqlite.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/d39d9b951ce3/
Changeset: d39d9b951ce3
User: dannon
Date: 2013-05-01 01:10:56
Summary: Fix conflicting util.sanitize_text import in controllers/admin.py
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/825cf4130d0e/
Changeset: 825cf4130d0e
User: dannon
Date: 2013-05-01 01:11:56
Summary: Use migrate_engine.execute() instead of the nonexistent db_session -- migration 0100
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/905d2c745ea2/
Changeset: 905d2c745ea2
User: dannon
Date: 2013-05-01 01:12:59
Summary: Remove commented out db_session creations.
Affected #: 35 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/01680aede3b8/
Changeset: 01680aede3b8
User: dannon
Date: 2013-05-01 01:18:37
Summary: Migration 0062 -- fix db_session/migrate_engine change.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/921d6de41db0/
Changeset: 921d6de41db0
User: dannon
Date: 2013-05-01 01:54:45
Summary: Migration script 0102, skip dropping uninstalled column in tool_dependency table under sqlite -- sqlalchemy_migrate check constraint boolean issue causes total failure, dropping of the table.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/c46d23ca1fba/
Changeset: c46d23ca1fba
User: dannon
Date: 2013-05-01 02:18:29
Summary: Prevent ambiguous util import in requests_common.py, clean up other imports.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/a576bc133d10/
Changeset: a576bc133d10
User: dannon
Date: 2013-05-01 02:19:00
Summary: Sort imports.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/15741f359890/
Changeset: 15741f359890
User: dannon
Date: 2013-05-01 02:22:46
Summary: Async controller -- clean up imports, remove *'s, fix potentially ambiguous util import.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/a0f0be48b6ae/
Changeset: a0f0be48b6ae
User: dannon
Date: 2013-05-01 05:24:55
Summary: Functional test setup fix for sqlite -- pool_size is an invalid option in sqlalchemy7+.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/a0b42d693905/
Changeset: a0b42d693905
User: dannon
Date: 2013-05-01 06:04:56
Summary: Admin controller -- fix ambiguous 'util' import; remove all import *'s and refactor
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/34e803f4780e/
Changeset: 34e803f4780e
User: dannon
Date: 2013-05-01 06:05:14
Summary: History controller -- fix ambiguous 'util' import; remove all import *'s and refactor
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/1e056f107ed8/
Changeset: 1e056f107ed8
User: dannon
Date: 2013-05-01 06:14:41
Summary: LibraryAdmin controller - fix ambiguous util imports, remove * imports.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/40859e3e342f/
Changeset: 40859e3e342f
User: dannon
Date: 2013-05-01 06:16:08
Summary: LibraryAdmin: Remove python 2.5 'set' compatability cruft.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/a3aefe9c4e12/
Changeset: a3aefe9c4e12
User: dannon
Date: 2013-05-01 06:24:08
Summary: Remove import * in base admin controller. Also fixes ambiguous 'util'
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/83d68671f55f/
Changeset: 83d68671f55f
User: dannon
Date: 2013-05-01 06:24:56
Summary: Remove commented cruft left over from refactoring.
Affected #: 2 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/bc525c2a6324/
Changeset: bc525c2a6324
User: dannon
Date: 2013-05-01 06:25:25
Summary: Merge
Affected #: 8 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/8a41333e136e/
Changeset: 8a41333e136e
User: dannon
Date: 2013-05-01 06:51:30
Summary: Refactor import *'s in library_common; fixes ambiguous util in namespace
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/06ada1cc941b/
Changeset: 06ada1cc941b
User: dannon
Date: 2013-05-01 06:52:57
Summary: Eliminate year old debugging code for library timing.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/7eb20069db80/
Changeset: 7eb20069db80
User: dannon
Date: 2013-05-01 20:01:35
Summary: Silence log.debug outputs for get_history() returning None, since it's both valid and fairly common.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/8b6a0c0f1fa8/
Changeset: 8b6a0c0f1fa8
User: dannon
Date: 2013-05-01 22:28:34
Summary: Remove * import, fixes duplicate 'util' import from sqlalchemy
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/6a0bbaec9518/
Changeset: 6a0bbaec9518
User: dannon
Date: 2013-05-01 22:29:18
Summary: Fix quota manager to flush properly when 'flush_needed' is set.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/556cf543e6b5/
Changeset: 556cf543e6b5
User: dannon
Date: 2013-05-01 22:59:29
Summary: Remove spurious 'Tool did not define error code...' debug statement -- not useful, almost nothing defines one.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/992d80a121d2/
Changeset: 992d80a121d2
User: dannon
Date: 2013-05-01 23:13:42
Summary: Remove duplicate imports from tags controller
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/867a491271c9/
Changeset: 867a491271c9
User: dannon
Date: 2013-05-02 04:32:57
Summary: library_common: Fix StreamBall import mangled previously.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/8decea3601cf/
Changeset: 8decea3601cf
User: dannon
Date: 2013-05-02 05:16:57
Summary: Tag controller: Fix abstract query to correctly map to item_class.id instead of strings. This resolves 'ambiguous column' issues.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/86ec749724eb/
Changeset: 86ec749724eb
User: dannon
Date: 2013-05-02 05:19:36
Summary: Library Security, update query for retrieving items.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/a8affc656b7a/
Changeset: a8affc656b7a
User: dannon
Date: 2013-05-02 06:41:04
Summary: Update toolshed migrations to work with recent sqlalchemy-migrate.
Affected #: 18 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/42b8b46051ff/
Changeset: 42b8b46051ff
User: dannon
Date: 2013-05-02 06:44:01
Summary: Strip trailing whitespace from toolshed migrations.
Affected #: 16 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/f0913a8a851f/
Changeset: f0913a8a851f
User: dannon
Date: 2013-05-02 06:46:28
Summary: Strip trailing whitespace from galaxy migrations.
Affected #: 64 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/013988cc1252/
Changeset: 013988cc1252
User: dannon
Date: 2013-05-02 15:15:24
Summary: Remove assign_mapper usage in migrate0005 -- was succeeding previously due to a left-behind assign_mapper.pyc
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/8ff0e63b00ac/
Changeset: 8ff0e63b00ac
User: dannon
Date: 2013-05-02 16:01:35
Summary: Update toolshed mappings to use regular mapper, vs assign_mapper
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/93469936a3c0/
Changeset: 93469936a3c0
User: dannon
Date: 2013-05-02 16:45:44
Summary: Fix toolshed functional tests to not use 'pool_size' with sqlite
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/a32f714d8b1d/
Changeset: a32f714d8b1d
User: dannon
Date: 2013-05-02 17:52:23
Summary: Fix category queries in toolshed repository controller
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/3d69ec4cf0e2/
Changeset: 3d69ec4cf0e2
User: dannon
Date: 2013-05-02 18:22:12
Summary: Merge with -central
Affected #: 37 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/44a7f7d0f607/
Changeset: 44a7f7d0f607
User: dannon
Date: 2013-05-02 18:51:50
Summary: Fix (hack) for a suspected circular import preventing tool shed functional tests from running in some environments
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/62c7b3379f10/
Changeset: 62c7b3379f10
User: dannon
Date: 2013-05-02 19:23:57
Summary: Model: galaxy.util.as_bool absolute import, fix from bad merge.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/ee075fec3e42/
Changeset: ee075fec3e42
User: dannon
Date: 2013-05-02 19:26:20
Summary: viz/genomes: Fix query.get()
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/cfb896a3558e/
Changeset: cfb896a3558e
User: dannon
Date: 2013-05-02 19:27:52
Summary: base admin controller: Fix query.get()
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/732ad82a75f0/
Changeset: 732ad82a75f0
User: dannon
Date: 2013-05-02 19:29:02
Summary: data manager controller: Fix query.get()
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/3c0497c86f98/
Changeset: 3c0497c86f98
User: dannon
Date: 2013-05-02 19:30:47
Summary: root controller: Fix query.get()
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/259949f32a32/
Changeset: 259949f32a32
User: dannon
Date: 2013-05-02 19:32:26
Summary: library common: Fix query.get()
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/9dfa253aa709/
Changeset: 9dfa253aa709
User: dannon
Date: 2013-05-02 19:34:06
Summary: visualization controller: Fix query.get()
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/872a9e3780d3/
Changeset: 872a9e3780d3
User: dannon
Date: 2013-05-02 19:48:56
Summary: Fix all but the metadata.py assign_mapper-> object.get() query issue -- should be the last one
Affected #: 3 files
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/07e265b822e8/
Changeset: 07e265b822e8
User: dannon
Date: 2013-05-02 19:55:34
Summary: Remove commented out debugging cruft in model/mapping.py
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/8149ff6f163d/
Changeset: 8149ff6f163d
User: dannon
Date: 2013-05-02 20:30:25
Summary: Model whitespace cleanup.
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/fcdb1361eb71/
Changeset: fcdb1361eb71
User: dannon
Date: 2013-05-02 20:30:40
Summary: merge
Affected #: 1 file
Diff not available.
https://bitbucket.org/galaxy/galaxy-central/commits/d2a4a4e41650/
Changeset: d2a4a4e41650
User: dannon
Date: 2013-05-02 21:33:15
Summary: Merge
Affected #: 9 files
Diff not available.
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: greg: Attempt to standardize the main page title for repository pages in the tool shed by displaying the repository name.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/2de7ce3e39fd/
Changeset: 2de7ce3e39fd
User: greg
Date: 2013-05-02 21:20:02
Summary: Attempt to standardize the main page title for repository pages in the tool shed by displaying the repository name.
Affected #: 8 files
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/browse_repository.mako
--- a/templates/webapps/tool_shed/repository/browse_repository.mako
+++ b/templates/webapps/tool_shed/repository/browse_repository.mako
@@ -39,7 +39,7 @@
%if can_browse_contents:
<div class="toolForm">
- <div class="toolFormTitle">Browse ${repository.name | h} revision ${repository.tip( trans.app ) | h} (repository tip)</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}' revision ${repository.tip( trans.app ) | h} (repository tip)</div>
%if can_download:
<div class="form-row"><label>Clone this repository:</label>
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/preview_tools_in_changeset.mako
--- a/templates/webapps/tool_shed/repository/preview_tools_in_changeset.mako
+++ b/templates/webapps/tool_shed/repository/preview_tools_in_changeset.mako
@@ -31,7 +31,7 @@
%endif
<div class="toolForm">
- <div class="toolFormTitle">Repository ${repository.name | h}</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}'</div><div class="toolFormBody">
%if len( changeset_revision_select_field.options ) > 1:
<form name="change_revision" id="change_revision" action="${h.url_for( controller='repository', action='preview_tools_in_changeset', repository_id=trans.security.encode_id( repository.id ) )}" method="post" >
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/rate_repository.mako
--- a/templates/webapps/tool_shed/repository/rate_repository.mako
+++ b/templates/webapps/tool_shed/repository/rate_repository.mako
@@ -64,7 +64,7 @@
</div><p/><div class="toolForm">
- <div class="toolFormTitle">Rate and Review</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}'</div><div class="toolFormBody"><form id="rate_repository" name="rate_repository" action="${h.url_for( controller='repository', action='rate_repository', id=trans.security.encode_id( repository.id ) )}" method="post"><div class="form-row">
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/upload.mako
--- a/templates/webapps/tool_shed/repository/upload.mako
+++ b/templates/webapps/tool_shed/repository/upload.mako
@@ -41,12 +41,12 @@
${render_tool_shed_repository_actions( repository=repository)}
<div class="toolForm">
- <div class="toolFormTitle">Upload a single file or a tarball</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}'</div><div class="toolFormBody"><div class="form-row"><div class="warningmessage">
- Uploading may take a while, depending upon the size of the file. Wait until a message is displayed in your
- browser after clicking the <b>Upload</b> button below.
+ Upload a single file or tarball. Uploading may take a while, depending upon the size of the file.
+ Wait until a message is displayed in your browser after clicking the <b>Upload</b> button below.
</div><div style="clear: both"></div></div>
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/view_changelog.mako
--- a/templates/webapps/tool_shed/repository/view_changelog.mako
+++ b/templates/webapps/tool_shed/repository/view_changelog.mako
@@ -38,7 +38,7 @@
%if can_download:
<div class="toolForm">
- <div class="toolFormTitle">${repository.name | h}</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}'</div><div class="toolFormBody"><div class="form-row"><label>Clone this repository:</label>
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/view_changeset.mako
--- a/templates/webapps/tool_shed/repository/view_changeset.mako
+++ b/templates/webapps/tool_shed/repository/view_changeset.mako
@@ -37,7 +37,7 @@
%if can_download:
<div class="toolForm">
- <div class="toolFormTitle">${repository.name | h}</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}'</div><div class="toolFormBody"><div class="form-row"><label>Clone this repository:</label>
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/view_repository.mako
--- a/templates/webapps/tool_shed/repository/view_repository.mako
+++ b/templates/webapps/tool_shed/repository/view_repository.mako
@@ -80,7 +80,7 @@
<p/>
%endif
<div class="toolForm">
- <div class="toolFormTitle">Repository '${repository.name}'</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}'</div><div class="toolFormBody"><div class="form-row"><label>${sharable_link_label}</label>
diff -r ae52981af216ff749092ccf16f254e77e8c096fa -r 2de7ce3e39fd08c39d32ff47bab2dd1993388ba9 templates/webapps/tool_shed/repository/view_tool_metadata.mako
--- a/templates/webapps/tool_shed/repository/view_tool_metadata.mako
+++ b/templates/webapps/tool_shed/repository/view_tool_metadata.mako
@@ -47,7 +47,7 @@
<p/>
%if can_download:
<div class="toolForm">
- <div class="toolFormTitle">Repository '${repository.name}'</div>
+ <div class="toolFormTitle">Repository '${repository.name | h}'</div><div class="toolFormBody"><div class="form-row"><label>Clone this repository:</label>
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: jgoecks: Trackster: add editable min, max labels to tracks.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/ae52981af216/
Changeset: ae52981af216
User: jgoecks
Date: 2013-05-02 21:14:50
Summary: Trackster: add editable min, max labels to tracks.
Affected #: 1 file
diff -r 262842a3689a77687ed3310ce180f5323e32b1b5 -r ae52981af216ff749092ccf16f254e77e8c096fa static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -2853,7 +2853,10 @@
/**
* Actions to be taken before drawing.
*/
- before_draw: function() {},
+ before_draw: function() {
+ // Clear because this is set when drawing.
+ this.max_height_px = 0;
+ },
/**
* Draw track. It is possible to force a redraw rather than use cached tiles and/or clear old
@@ -2930,11 +2933,15 @@
/**
* Add a maximum/minimum label to track.
*/
- _add_yaxis_label: function(type, val, pref_name) {
- var css_class = (type === 'max' ? 'top' : 'bottom'),
- text = (type === 'max' ? 'max' : 'min');
-
- var label = this.container_div.find(".yaxislabel." + css_class);
+ _add_yaxis_label: function(type, val, pref_name, on_change) {
+ var track = this,
+ css_class = (type === 'max' ? 'top' : 'bottom'),
+ text = (type === 'max' ? 'max' : 'min'),
+ // Default action for on_change is to redraw track.
+ on_change = on_change || function() {
+ track.request_draw(true);
+ },
+ label = this.container_div.find(".yaxislabel." + css_class);
if (label.length !== 0) {
// Label already exists, so update value.
@@ -2942,14 +2949,13 @@
}
else {
// Add label.
- var track = this;
label = $("<div/>").text(val).make_text_editable({
num_cols: 12,
on_finish: function(new_val) {
$(".bs-tooltip").remove();
var new_val = parseFloat(new_val);
track.prefs[ pref_name ] = (!isNaN(new_val) ? new_val : null);
- track.request_draw(true);
+ on_change();
},
help_text: "Set " + text + " value"
}).addClass('yaxislabel ' + css_class).css("color", this.prefs.label_color);
@@ -3337,6 +3343,9 @@
unpack_drawables: DrawableCollection.prototype.unpack_drawables,
+ /**
+ * Change mode for all tracks.
+ */
change_mode: function(new_mode) {
TiledTrack.prototype.change_mode.call(this, new_mode);
for (var i = 0; i < this.drawables.length; i++) {
@@ -3426,8 +3435,6 @@
// Set up and draw tile.
extend(tile_data, kwargs[ 'more_tile_data' ] );
- this.tile_predraw_init();
-
var canvas = track.view.canvas_manager.new_canvas(),
tile_low = region.get('start'),
tile_high = region.get('end'),
@@ -3518,9 +3525,11 @@
},
/**
- * Actions taken before drawing a tile.
+ * Actions taken before drawing.
*/
- tile_predraw_init: function() {
+ before_draw: function() {
+ TiledTrack.prototype.before_draw.call(this);
+
//
// Set min, max for LineTracks to be largest min, max.
//
@@ -3541,6 +3550,8 @@
}
}
}
+ this.prefs.min_value = min;
+ this.prefs.max_value = max;
// Set all tracks to smallest min, biggest max.
for (var i = 0; i < this.drawables.length; i++) {
@@ -3551,6 +3562,18 @@
},
/**
+ * Update minimum, maximum for component tracks.
+ */
+ update_all_min_max: function() {
+ var track = this;
+ _.each(this.drawables, function(d) {
+ d.prefs.min_value = track.prefs.min_value;
+ d.prefs.max_value = track.prefs.max_value;
+ });
+ this.request_draw(true);
+ },
+
+ /**
* Actions to be taken after draw has been completed. Draw is completed when all tiles have been
* drawn/fetched and shown.
*/
@@ -3572,7 +3595,15 @@
this.draw_helper(true, tile.region, tile.resolution, tile.html_elt.parent(), w_scale, { height: max_height } );
tile.html_elt.remove();
}
- }
+ }
+
+ // Wrap function so that it can be called without object reference.
+ var track = this,
+ t = function() { track.update_all_min_max(); };
+
+ // Add min, max labels.
+ this._add_yaxis_label('min', this.drawables[0].prefs.min_value, 'min_value', t);
+ this._add_yaxis_label('max', this.drawables[0].prefs.max_value, 'max_value', t);
}
});
@@ -3701,6 +3732,12 @@
},
/**
+ * Actions to be taken before drawing.
+ */
+ // FIXME: can the default behavior be used; right now it breaks during resize.
+ before_draw: function() {},
+
+ /**
* Draw LineTrack tile.
*/
draw_tile: function(result, ctx, mode, resolution, region, w_scale) {
@@ -3843,14 +3880,6 @@
},
/**
- * Actions to be taken before drawing.
- */
- before_draw: function() {
- // Clear because this is set when drawing.
- this.max_height_px = 0;
- },
-
- /**
* Actions to be taken after draw has been completed. Draw is completed when all tiles have been
* drawn/fetched and shown.
*/
@@ -4211,14 +4240,6 @@
},
/**
- * Actions to be taken before drawing.
- */
- before_draw: function() {
- // Clear because this is set when drawing.
- this.max_height_px = 0;
- },
-
- /**
* Additional initialization required before drawing track for the first time.
*/
predraw_init: function() {
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: jgoecks: Trackster: implement generic functionality for adding and editing track min/max values. Also redraw by default on resize.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/262842a3689a/
Changeset: 262842a3689a
User: jgoecks
Date: 2013-05-02 19:15:02
Summary: Trackster: implement generic functionality for adding and editing track min/max values. Also redraw by default on resize.
Affected #: 1 file
diff -r f7a2d117ad02430426fef338f991f063853c377e -r 262842a3689a77687ed3310ce180f5323e32b1b5 static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -2442,7 +2442,9 @@
/**
* Action to take during resize.
*/
- on_resize: function() {},
+ on_resize: function() {
+ this.request_draw(true);
+ },
/**
* Add resizing handle to drawable's container_div.
@@ -2926,6 +2928,36 @@
},
/**
+ * Add a maximum/minimum label to track.
+ */
+ _add_yaxis_label: function(type, val, pref_name) {
+ var css_class = (type === 'max' ? 'top' : 'bottom'),
+ text = (type === 'max' ? 'max' : 'min');
+
+ var label = this.container_div.find(".yaxislabel." + css_class);
+
+ if (label.length !== 0) {
+ // Label already exists, so update value.
+ label.text(val);
+ }
+ else {
+ // Add label.
+ var track = this;
+ label = $("<div/>").text(val).make_text_editable({
+ num_cols: 12,
+ on_finish: function(new_val) {
+ $(".bs-tooltip").remove();
+ var new_val = parseFloat(new_val);
+ track.prefs[ pref_name ] = (!isNaN(new_val) ? new_val : null);
+ track.request_draw(true);
+ },
+ help_text: "Set " + text + " value"
+ }).addClass('yaxislabel ' + css_class).css("color", this.prefs.label_color);
+ this.container_div.prepend(label);
+ }
+ },
+
+ /**
* Actions to be taken after draw has been completed. Draw is completed when all tiles have been
* drawn/fetched and shown.
*/
@@ -2947,27 +2979,13 @@
}
//
- // If using SummaryTree tiles, show max and make it editable.
+ // If using SummaryTree tiles, show max.
//
var track = this,
first_tile = tiles[0];
if (first_tile instanceof SummaryTreeTile) {
- // Remove old max.
- this.container_div.find(".yaxislabel").remove();
-
- // Add new max.
- var max_val = (this.prefs.histogram_max ? this.prefs.histogram_max : first_tile.max_val),
- max_label = $("<div/>").text(max_val).make_text_editable({
- num_cols: 12,
- on_finish: function(new_val) {
- $(".bs-tooltip").remove();
- var new_val = parseFloat(new_val);
- track.prefs.histogram_max = (!isNaN(new_val) ? new_val : null);
- track.request_draw(true);
- },
- help_text: "Set max value; leave blank to use default"
- }).addClass('yaxislabel top').css("color", this.prefs.label_color);
- this.container_div.prepend(max_label);
+ var max_val = (this.prefs.histogram_max ? this.prefs.histogram_max : first_tile.max_val);
+ this._add_yaxis_label('max', max_val, 'histogram_max');
}
},
@@ -3496,7 +3514,7 @@
// Replace track with group.
var index = this.container.replace_drawable(this, group, true);
- group.request_draw();
+ group.request_draw(true);
},
/**
@@ -3647,8 +3665,7 @@
onchange: function() {
track.set_name(track.prefs.name);
track.vertical_range = track.prefs.max_value - track.prefs.min_value;
- track.set_min_value(track.prefs.min_value);
- track.set_max_value(track.prefs.max_value);
+ track.request_redraw(true);
}
});
@@ -3657,30 +3674,6 @@
this.vertical_range = this.config.values.max_value - this.config.values.min_value;
};
extend(LineTrack.prototype, Drawable.prototype, TiledTrack.prototype, {
- /**
- * Action to take during resize.
- */
- on_resize: function() {
- this.request_draw(true);
- },
-
- /**
- * Set track minimum value.
- */
- set_min_value: function(new_val) {
- this.prefs.min_value = new_val;
- $('#linetrack_' + this.dataset.id + '_minval').text(this.prefs.min_value);
- this.request_draw(true);
- },
-
- /**
- * Set track maximum value.
- */
- set_max_value: function(new_val) {
- this.prefs.max_value = new_val;
- $('#linetrack_' + this.dataset.id + '_maxval').text(this.prefs.max_value);
- this.request_draw(true);
- },
predraw_init: function() {
var track = this;
@@ -3701,45 +3694,9 @@
// Update the prefs
track.prefs.min_value = min_value;
track.prefs.max_value = max_value;
- // Update the config
- // FIXME: we should probably only save this when the user explicately sets it
- // since we lose the ability to compute it on the fly (when changing
- // chromosomes for example).
- $('#track_' + track.dataset.id + '_minval').val(track.prefs.min_value);
- $('#track_' + track.dataset.id + '_maxval').val(track.prefs.max_value);
}
track.vertical_range = track.prefs.max_value - track.prefs.min_value;
track.total_frequency = data.total_frequency;
-
- // Draw y-axis labels if necessary
- track.container_div.find(".yaxislabel").remove();
-
- // Add min, max labels.
- var
- min_label = $("<div/>").text(round(track.prefs.min_value, 3)).make_text_editable({
- num_cols: 6,
- on_finish: function(new_val) {
- $(".bs-tooltip").remove();
- var new_val = parseFloat(new_val);
- if (!isNaN(new_val)) {
- track.set_min_value(new_val);
- }
- },
- help_text: "Set min value"
- }).addClass('yaxislabel bottom').attr("id", 'linetrack_' + track.dataset.id + '_minval')
- .prependTo(track.container_div),
- max_label = $("<div/>").text(round(track.prefs.max_value, 3)).make_text_editable({
- num_cols: 6,
- on_finish: function(new_val) {
- $(".bs-tooltip").remove();
- var new_val = parseFloat(new_val);
- if (!isNaN(new_val)) {
- track.set_max_value(new_val);
- }
- },
- help_text: "Set max value"
- }).addClass('yaxislabel top').attr("id", 'linetrack_' + track.dataset.id + '_maxval')
- .prependTo(track.container_div);
});
},
@@ -3763,6 +3720,15 @@
*/
can_subset: function(entry) {
return (entry.data[1][0] - entry.data[0][0] === 1);
+ },
+
+ /**
+ * Add min, max labels.
+ */
+ postdraw_actions: function(tiles, width, w_scale, clear_after) {
+ // Add min, max labels.
+ this._add_yaxis_label('max', round(this.prefs.max_value, 3), 'max_value');
+ this._add_yaxis_label('min', round(this.prefs.min_value, 3), 'min_value');
}
});
@@ -3788,8 +3754,7 @@
onchange: function() {
track.set_name(track.prefs.name);
track.vertical_range = track.prefs.max_value - track.prefs.min_value;
- track.set_min_value(track.prefs.min_value);
- track.set_max_value(track.prefs.max_value);
+ this.request_redraw(true);
}
});
@@ -3799,27 +3764,6 @@
};
extend(DiagonalHeatmapTrack.prototype, Drawable.prototype, TiledTrack.prototype, {
/**
- * Action to take during resize.
- */
- on_resize: function() {
- this.request_draw(true);
- },
- /**
- * Set track minimum value.
- */
- set_min_value: function(new_val) {
- this.prefs.min_value = new_val;
- this.request_draw(true);
- },
- /**
- * Set track maximum value.
- */
- set_max_value: function(new_val) {
- this.prefs.max_value = new_val;
- this.request_draw(true);
- },
-
- /**
* Draw tile.
*/
draw_tile: function(result, ctx, mode, resolution, region, w_scale) {
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: greg: Fix for generating a repository dependency key when prior installation required is true.
by commits-noreply@bitbucket.org 02 May '13
by commits-noreply@bitbucket.org 02 May '13
02 May '13
1 new commit in galaxy-central:
https://bitbucket.org/galaxy/galaxy-central/commits/f7a2d117ad02/
Changeset: f7a2d117ad02
User: greg
Date: 2013-05-02 17:57:42
Summary: Fix for generating a repository dependency key when prior installation required is true.
Affected #: 2 files
diff -r a26ec089b62fc2eb4824e738b7cc668b481de184 -r f7a2d117ad02430426fef338f991f063853c377e lib/tool_shed/util/repository_dependency_util.py
--- a/lib/tool_shed/util/repository_dependency_util.py
+++ b/lib/tool_shed/util/repository_dependency_util.py
@@ -256,12 +256,34 @@
message = '%s ' % str( error )
return message
-def get_key_for_repository_changeset_revision( toolshed_base_url, repository, repository_metadata ):
- return container_util.generate_repository_dependencies_key_for_repository( toolshed_base_url=toolshed_base_url,
- repository_name=repository.name,
- repository_owner=repository.user.username,
- changeset_revision=repository_metadata.changeset_revision,
- prior_installation_required=False )
+def get_key_for_repository_changeset_revision( toolshed_base_url, repository, repository_metadata, all_repository_dependencies ):
+ prior_installation_required = get_prior_installation_required_for_key( toolshed_base_url, repository, repository_metadata, all_repository_dependencies )
+ # Create a key with the value of prior_installation_required defaulted to False.
+ key = container_util.generate_repository_dependencies_key_for_repository( toolshed_base_url=toolshed_base_url,
+ repository_name=repository.name,
+ repository_owner=repository.user.username,
+ changeset_revision=repository_metadata.changeset_revision,
+ prior_installation_required=prior_installation_required )
+ return key
+
+def get_prior_installation_required_for_key( toolshed_base_url, repository, repository_metadata, all_repository_dependencies ):
+ """
+ If all_repository_dependencies contains a repository dependency tuple that is associated with the received repository, return the
+ value of the tuple's prior_installation_required component.
+ """
+ rd_tuple = ( toolshed_base_url, repository.name, repository.user.username, repository_metadata.changeset_revision )
+ for rd_key, rd_tups in all_repository_dependencies.items():
+ if rd_key in [ 'root_key', 'description' ]:
+ continue
+ for rd_tup in rd_tups:
+ rd_toolshed, rd_name, rd_owner, rd_changeset_revision, rd_prior_installation_required = suc.parse_repository_dependency_tuple( rd_tup )
+ if rd_toolshed == toolshed_base_url and \
+ rd_name == repository.name and \
+ rd_owner == repository.user.username and \
+ rd_changeset_revision == repository_metadata.changeset_revision:
+ return rd_prior_installation_required
+ # Default prior_installation_required to False.
+ return False
def get_repository_dependencies_for_changeset_revision( trans, repository, repository_metadata, toolshed_base_url,
key_rd_dicts_to_be_processed=None, all_repository_dependencies=None,
@@ -285,7 +307,7 @@
metadata = repository_metadata.metadata
if metadata:
if 'repository_dependencies' in metadata:
- current_repository_key = get_key_for_repository_changeset_revision( toolshed_base_url, repository, repository_metadata )
+ current_repository_key = get_key_for_repository_changeset_revision( toolshed_base_url, repository, repository_metadata, all_repository_dependencies )
repository_dependencies_dict = metadata[ 'repository_dependencies' ]
if not all_repository_dependencies:
all_repository_dependencies = initialize_all_repository_dependencies( current_repository_key,
@@ -554,7 +576,7 @@
# Change the folder label from 'Missing repository dependencies' to be 'Repository dependencies' for display.
root_container = containers_dict[ 'missing_repository_dependencies' ]
for sub_container in root_container.folders:
- # There should only be 1 subfolder.
+ # There should only be 1 sub-folder.
sub_container.label = 'Repository dependencies'
containers_dict[ 'repository_dependencies' ] = root_container
containers_dict[ 'missing_repository_dependencies' ] = None
@@ -608,8 +630,8 @@
def prune_invalid_repository_dependencies( repository_dependencies ):
"""
- Eliminate all invalid entries in the received repository_dependencies dictionary. An entry is invalid if if the value_list of the key/value pair is
- empty. This occurs when an invalid combination of tool shed, name , owner, changeset_revision is used and a repository_metadata reocrd is not found.
+ Eliminate all invalid entries in the received repository_dependencies dictionary. An entry is invalid if the value_list of the key/value pair is
+ empty. This occurs when an invalid combination of tool shed, name , owner, changeset_revision is used and a repository_metadata record is not found.
"""
valid_repository_dependencies = {}
description = repository_dependencies.get( 'description', None )
diff -r a26ec089b62fc2eb4824e738b7cc668b481de184 -r f7a2d117ad02430426fef338f991f063853c377e templates/webapps/tool_shed/repository/common.mako
--- a/templates/webapps/tool_shed/repository/common.mako
+++ b/templates/webapps/tool_shed/repository/common.mako
@@ -980,6 +980,7 @@
</div>
%endif
%if tool_test_results_root_folder:
+ <p/><div class="toolForm"><div class="toolFormTitle">Automated tool test results</div><div class="toolFormBody">
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/0b5c9c031f72/
Changeset: 0b5c9c031f72
User: jgoecks
Date: 2013-05-02 16:33:28
Summary: Trackster: remove nodraw parameter because it is no longer needed.
Affected #: 1 file
diff -r 72a381a4f692feb906e85f6cfed99c7407640282 -r 0b5c9c031f72526d506cb5acf55fb79ec0af1732 static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -892,7 +892,7 @@
],
saved_values: obj_dict.prefs,
onchange: function() {
- track.request_redraw(false, true);
+ track.request_redraw(true);
}
});
},
@@ -1266,8 +1266,7 @@
view.chrom_select.val(view.chrom);
view.max_high = found.len-1; // -1 because we're using 0-based indexing.
view.reset();
- view.request_redraw(true);
-
+
for (var i = 0, len = view.drawables.length; i < len; i++) {
var drawable = view.drawables[i];
if (drawable.init) {
@@ -1392,8 +1391,7 @@
* Request that view redraw some or all tracks. If a track is not specificied, redraw all tracks.
*/
// FIXME: change method call so that track is first and additional parameters are optional.
- // FIXME: is nodraw parameter needed?
- request_redraw: function(nodraw, force, clear_after, a_track) {
+ request_redraw: function(force, clear_after, a_track) {
var
view = this,
// Either redrawing a single drawable or all view's drawables.
@@ -1428,7 +1426,7 @@
// Set up redraw if it has not been requested since last redraw.
if (!this.requested_redraw) {
- requestAnimationFrame(function() { view._redraw(nodraw); });
+ requestAnimationFrame(function() { view._redraw(); });
this.requested_redraw = true;
}
},
@@ -1437,7 +1435,7 @@
* NOTE: this method should never be called directly; request_redraw() should be used so
* that requestAnimationFrame can manage redrawing.
*/
- _redraw: function(nodraw) {
+ _redraw: function() {
// TODO: move this code to function that does location setting.
// Clear because requested redraw is being handled now.
@@ -1482,20 +1480,18 @@
this.overview_highlight.css({ left: left_px, width: width_px });
}
- if (!nodraw) {
- var track, force, clear_after;
- for (var i = 0, len = this.tracks_to_be_redrawn.length; i < len; i++) {
- track = this.tracks_to_be_redrawn[i][0];
- force = this.tracks_to_be_redrawn[i][1];
- clear_after = this.tracks_to_be_redrawn[i][2];
- if (track) {
- track._draw(force, clear_after);
- }
+ var track, force, clear_after;
+ for (var i = 0, len = this.tracks_to_be_redrawn.length; i < len; i++) {
+ track = this.tracks_to_be_redrawn[i][0];
+ force = this.tracks_to_be_redrawn[i][1];
+ clear_after = this.tracks_to_be_redrawn[i][2];
+ if (track) {
+ track._draw(force, clear_after);
}
- this.tracks_to_be_redrawn = [];
- for (i = 0, len = this.label_tracks.length; i < len; i++) {
- this.label_tracks[i]._draw();
- }
+ }
+ this.tracks_to_be_redrawn = [];
+ for (i = 0, len = this.label_tracks.length; i < len; i++) {
+ this.label_tracks[i]._draw();
}
},
zoom_in: function (point, container) {
@@ -2848,7 +2844,7 @@
* Request that track be drawn.
*/
request_draw: function(force, clear_after) {
- this.view.request_redraw(false, force, clear_after, this);
+ this.view.request_redraw(force, clear_after, this);
},
/**
https://bitbucket.org/galaxy/galaxy-central/commits/a26ec089b62f/
Changeset: a26ec089b62f
User: jgoecks
Date: 2013-05-02 16:58:19
Summary: Trackster: optionally clear tile cache when requesting a track redraw.
Affected #: 2 files
diff -r 0b5c9c031f72526d506cb5acf55fb79ec0af1732 -r a26ec089b62fc2eb4824e738b7cc668b481de184 static/scripts/viz/trackster/filters.js
--- a/static/scripts/viz/trackster/filters.js
+++ b/static/scripts/viz/trackster/filters.js
@@ -178,7 +178,7 @@
filter.manager.alpha_filter = null;
filter.transparency_icon.removeClass("active");
}
- filter.manager.track.request_draw(true, true);
+ filter.manager.track.request_draw(false, true, true);
} )
.appendTo(display_controls_div).hide();
this.height_icon = create_action_icon("Use filter for data height", "arrow-resize-090",
@@ -195,7 +195,7 @@
filter.manager.height_filter = null;
filter.height_icon.removeClass("active");
}
- filter.manager.track.request_draw(true, true);
+ filter.manager.track.request_draw(false, true, true);
} )
.appendTo(display_controls_div).hide();
filter.parent_div.hover( function() {
@@ -265,7 +265,7 @@
var self = this;
setTimeout(function() {
if (values[0] === self.low && values[1] === self.high) {
- self.manager.track.request_draw(true, true);
+ self.manager.track.request_draw(false, true, true);
}
}, 25);
diff -r 0b5c9c031f72526d506cb5acf55fb79ec0af1732 -r a26ec089b62fc2eb4824e738b7cc668b481de184 static/scripts/viz/trackster/tracks.js
--- a/static/scripts/viz/trackster/tracks.js
+++ b/static/scripts/viz/trackster/tracks.js
@@ -845,9 +845,9 @@
return obj_dict;
},
- request_draw: function(clear_after, force) {
+ request_draw: function(clear_tile_cache, force, clear_after) {
for (var i = 0; i < this.drawables.length; i++) {
- this.drawables[i].request_draw(clear_after, force);
+ this.drawables[i].request_draw(clear_tile_cache, force, clear_after);
}
}
});
@@ -1390,7 +1390,6 @@
/**
* Request that view redraw some or all tracks. If a track is not specificied, redraw all tracks.
*/
- // FIXME: change method call so that track is first and additional parameters are optional.
request_redraw: function(force, clear_after, a_track) {
var
view = this,
@@ -2101,7 +2100,7 @@
tile.stale = true;
track.data_manager.get_more_data(tile_region, track.mode, tile.resolution, {}, track.data_manager.DEEP_DATA_REQ);
$(".bs-tooltip").hide();
- track.request_draw(true);
+ track.request_draw(false, true);
}).dblclick(function(e) {
// Do not propogate as this would normally zoom in.
e.stopPropagation();
@@ -2112,7 +2111,7 @@
tile.stale = true;
track.data_manager.get_more_data(tile_region, track.mode, tile.resolution, {}, track.data_manager.BROAD_DATA_REQ);
$(".bs-tooltip").hide();
- track.request_draw(true);
+ track.request_draw(false, true);
}).dblclick(function(e) {
// Do not propogate as this would normally zoom in.
e.stopPropagation();
@@ -2786,8 +2785,7 @@
// TODO: is it necessary to store the mode in two places (.mode and track_config)?
track.mode = new_mode;
track.config.values['mode'] = new_mode;
- track.tile_cache.clear();
- track.request_draw();
+ track.request_draw(true);
this.action_icons.mode_icon.attr("title", "Set display mode (now: " + track.mode + ")");
return track;
},
@@ -2843,7 +2841,10 @@
/**
* Request that track be drawn.
*/
- request_draw: function(force, clear_after) {
+ request_draw: function(clear_tile_cache, force, clear_after) {
+ if (clear_tile_cache) {
+ this.tile_cache.clear();
+ }
this.view.request_redraw(force, clear_after, this);
},
@@ -2962,8 +2963,7 @@
$(".bs-tooltip").remove();
var new_val = parseFloat(new_val);
track.prefs.histogram_max = (!isNaN(new_val) ? new_val : null);
- track.tile_cache.clear();
- track.request_draw();
+ track.request_draw(true);
},
help_text: "Set max value; leave blank to use default"
}).addClass('yaxislabel top').css("color", this.prefs.label_color);
@@ -3670,8 +3670,7 @@
set_min_value: function(new_val) {
this.prefs.min_value = new_val;
$('#linetrack_' + this.dataset.id + '_minval').text(this.prefs.min_value);
- this.tile_cache.clear();
- this.request_draw();
+ this.request_draw(true);
},
/**
@@ -3680,8 +3679,7 @@
set_max_value: function(new_val) {
this.prefs.max_value = new_val;
$('#linetrack_' + this.dataset.id + '_maxval').text(this.prefs.max_value);
- this.tile_cache.clear();
- this.request_draw();
+ this.request_draw(true);
},
predraw_init: function() {
@@ -3811,16 +3809,14 @@
*/
set_min_value: function(new_val) {
this.prefs.min_value = new_val;
- this.tile_cache.clear();
- this.request_draw();
+ this.request_draw(true);
},
/**
* Set track maximum value.
*/
set_max_value: function(new_val) {
this.prefs.max_value = new_val;
- this.tile_cache.clear();
- this.request_draw();
+ this.request_draw(true);
},
/**
@@ -3874,9 +3870,8 @@
saved_values: obj_dict.prefs,
onchange: function() {
track.set_name(track.prefs.name);
- track.tile_cache.clear();
track.set_painter_from_config();
- track.request_draw();
+ track.request_draw(true);
}
});
this.prefs = this.config.values;
@@ -4210,8 +4205,7 @@
saved_values: obj_dict.prefs,
onchange: function() {
this.track.set_name(this.track.prefs.name);
- this.track.tile_cache.clear();
- this.track.request_draw();
+ this.track.request_draw(true);
}
});
this.prefs = this.config.values;
@@ -4369,8 +4363,7 @@
saved_values: obj_dict.prefs,
onchange: function() {
this.track.set_name(this.track.prefs.name);
- this.track.tile_cache.clear();
- this.track.request_draw();
+ this.track.request_draw(true);
}
});
this.prefs = this.config.values;
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