import SequenceServer from './sequenceserver';
import _ from 'underscore';
import React from 'react';
import d3 from 'd3';
import * as Helpers from './visualisation_helpers';
import GraphicalOverview from './alignmentsoverview';
//import Kablammo from './kablammo';
import './sequence';
import AlignmentExporter from './alignment_exporter';
//import LengthDistribution from './lengthdistribution';
//import Circos from './circos';
/**
* Dynamically create form and submit.
*/
var downloadFASTA = function (sequence_ids, database_ids) {
var form = $('
').attr('method', 'post').attr('action', '/get_sequence');
addField("sequence_ids", sequence_ids);
addField("database_ids", database_ids);
form.appendTo('body').submit().remove();
function addField(name, val) {
form.append(
$('').attr('type', 'hidden').attr('name', name).val(val)
);
}
}
/**
* Pretty formats number
*/
var Utils = {
/**
* Render URL for sequence-viewer.
*/
a: function (link) {
if (link.title && link.url)
{
return (
{link.icon && }
{" " + link.title + " "}
);
}
},
/***********************************
* Formatters for hits & hsp table *
***********************************/
// Formats an array of two elements as "first (last)".
format_2_tuple: function (tuple) {
return (tuple[0] + " (" + tuple[tuple.length - 1] + ")");
},
/**
* Returns fraction as percentage
*/
inPercentage: function (num , den) {
return (num * 100.0 / den).toFixed(2);
},
/**
* Returns fractional representation as String.
*/
inFraction: function (num , den) {
return num + "/" + den;
},
/**
* Returns given Float as String formatted to two decimal places.
*/
inTwoDecimal: function (num) {
return num.toFixed(2)
},
/**
* Returns zero if num is zero. Returns two decimal representation of num
* if num is between [1..10). Returns num in scientific notation otherwise.
*/
inExponential: function (num) {
// Nothing to do if num is 0.
if (num === 0) {
return 0
}
// Round to two decimal places if in the rane [1..10).
if (num >= 1 && num < 10)
{
return this.inTwoDecimal(num)
}
// Return numbers in the range [0..1) and [10..Inf] in
// scientific format.
var exp = num.toExponential(2);
var parts = exp.split("e");
var base = parts[0];
var power = parts[1];
return {base} × 10{power};
}
};
/**
* Component for sequence-viewer links.
*/
var SequenceViewer = (function () {
var Viewer = React.createClass({
/**
* The CSS class name that will be assigned to the widget container. ID
* assigned to the widget container is derived from the same.
*/
widgetClass: 'biojs-vis-sequence',
// Lifecycle methods. //
render: function () {
this.widgetID =
this.widgetClass + '-' + (new Date().getUTCMilliseconds());
return (
);
}
});
/**
* Renders report for each query sequence.
*
* Composed of graphical overview, tabular summary (HitsTable),
* and a list of Hits.
*/
var Query = React.createClass({
// Kind of public API //
/**
* Returns the id of query.
*/
domID: function () {
return "Query_" + this.props.query.number;
},
/**
* Returns number of hits.
*/
numhits: function () {
return this.props.query.hits.length;
},
// Life cycle methods //
render: function () {
return (
);
},
});
/**
* Renders entire report.
*
* Composed of Query and Sidebar components.
*/
var Report = React.createClass({
// Kind of public API //
/**
* Event-handler when hit is selected
* Adds glow to hit component.
* Updates number of Fasta that can be downloaded
*/
selectHit: function (id) {
var checkbox = $("#" + id);
var num_checked = $('.hit-links :checkbox:checked').length;
if (!checkbox || !checkbox.val()) {
return;
}
var $hit = $(checkbox.data('target'));
// Highlight selected hit and sync checkboxes if sequence viewer is open.
if (checkbox.is(":checked")) {
$hit
.addClass('glow')
.find(":checkbox").not(checkbox).check();
var $a = $('.download-fasta-of-selected');
var $b = $('.download-alignment-of-selected');
$b.enable()
var $n = $a.find('span');
$a
.enable()
}
else {
$hit
.removeClass('glow')
.find(":checkbox").not(checkbox).uncheck();
}
if (num_checked >= 1)
{
var $a = $('.download-fasta-of-selected');
var $b = $('.download-alignment-of-selected');
$a.find('.text-bold').html(num_checked);
$b.find('.text-bold').html(num_checked);
}
if (num_checked == 0) {
var $a = $('.download-fasta-of-selected');
var $b = $('.download-alignment-of-selected');
$a.addClass('disabled').find('.text-bold').html('');
$b.addClass('disabled').find('.text-bold').html('');
}
},
// Internal helpers. //
/**
* Fetch results.
*/
fetch_results: function () {
var intervals = [200, 400, 800, 1200, 2000, 3000, 5000];
$.getJSON(location.pathname + '.json')
.complete(_.bind(function (jqXHR) {
switch (jqXHR.status) {
case 202:
var interval;
if (intervals.length === 1) {
interval = intervals[0];
}
else {
interval = intervals.shift;
}
setTimeout(this.fetch_results, interval);
break;
case 200:
this.setState(jqXHR.responseJSON);
break;
case 500:
SequenceServer.showErrorModal(jqXHR, function () {});
break;
}
}, this));
},
/**
* Returns true if results have been fetched.
*
* A holding message is shown till results are fetched.
*/
isResultAvailable: function () {
return this.state.queries.length >= 1;
},
/**
* Returns true if sidebar should be shown.
*
* Sidebar is not shown if there is only one query and there are no hits
* corresponding to the query.
*/
shouldShowSidebar: function () {
return !(this.state.queries.length == 1 &&
this.state.queries[0].hits.length == 0);
},
loading: function () {
return (
BLAST-ing
This can take some time depending on the size of your query and
database(s). The page will update automatically when BLAST is
done.
You can bookmark the page and come back to it later or share
the link with someone.