Example #1
0
def compare():
    # if proj among arguments, show this tree first.
    try:
        proj_a = int(request.args.get('proj_a', None))
        proj_b = int(request.args.get('proj_b', None))
    except (TypeError, ValueError):
        proj_a = proj_b = None
    include = request.args.get('include', None)

    # list of projects (and proj_names) used to create dropdown project selector
    upload_list = UserFile.query.filter_by(user_id=current_user.id).\
        filter_by(run_complete=True).order_by(UserFile.file_id).all()

    if len(upload_list) > 1:
        # Use specified project from args or highest file_id as CURRENT PROJECT
        current_proj = upload_list[-1]  # override if valid proj specified
        if proj_a and proj_b:
            current_temp_a = [u for u in upload_list if u.file_id == proj_a]
            current_temp_b = [u for u in upload_list if u.file_id == proj_b]
            # if not among user's finished projects, use highest file_id
            if len(current_temp_a) == 1 and len(current_temp_b) == 1:
                current_proj_a = current_temp_a[0]
                current_proj_b = current_temp_b[0]
            else:
                current_proj_a = upload_list[-2]
                current_proj_b = upload_list[-1]
        else:
            current_proj_a = upload_list[-2]
            current_proj_b = upload_list[-1]
        detail_path1 = naming_rules.get_detailed_path(current_proj_a)
        detail_path2 = naming_rules.get_detailed_path(current_proj_b)
        js_name1 = naming_rules.get_js_name(current_proj_a)
        js_name2 = naming_rules.get_js_name(current_proj_b)
        xlabel = u"Effect size ({})".format(current_proj_a.get_fancy_filename())
        ylabel = u"Effect size ({})".format(current_proj_b.get_fancy_filename())

        # load pathways with 1+ mutation in 1+ patients,
        # ignoring ones with 'cancer' etc in name
        all_paths1 = load_pathway_list_from_file(detail_path1)
        all_paths2 = load_pathway_list_from_file(detail_path2)

        # IDs with p<0.05 and +ve effect
        sig_p = OrderedDict(
            [(i.path_id, i.nice_name) for i in all_paths1 if i.gene_set])
        sig_pids1 = [i for i in sig_p]
        sig_p2 = OrderedDict(
            [(i.path_id, i.nice_name) for i in all_paths2 if i.gene_set])
        sig_pids2 = [i for i in sig_p2]
        sig_p.update(sig_p2)  # ORDERED by proj1 effect size

        # BUILD DATAFRAME WITH ALL sig PATHWAYS, proj1 object order.
        pway_names = sig_p.values()  # order important
        columns = ['path_id', 'pname', 'ind1', 'ind2', 'e1', 'e2', 'e1_only',
                   'e2_only', 'q1', 'q2']
        df = pd.DataFrame(index=sig_p.keys(), data={'pname': pway_names},
                          columns=columns)
        for path_group, evar, qvar, ind, sigs in \
                [(all_paths1, 'e1', 'q1', 'ind1', sig_pids1),
                 (all_paths2, 'e2', 'q2', 'ind2', sig_pids2)]:
            for path in path_group:
                path_id = path.path_id
                if path_id not in sig_p:
                    continue
                df.loc[path_id, evar] = get_effect(path)
                df.loc[path_id, qvar] = get_q(path)
                temp_ind = sigs.index(path_id) if path_id in sigs else -1
                df.loc[path_id, ind] = temp_ind
        df.ind1.fillna(-1, inplace=True)
        df.ind2.fillna(-1, inplace=True)
        df.e1_only = df.where(df.e2.isnull())['e1']
        df.e2_only = df.where(df.e1.isnull())['e2']

        inds1 = list(df.ind1)
        inds2 = list(df.ind2)

        source = ColumnDataSource(data=df)
        source_full = ColumnDataSource(data=df)
        source.name, source_full.name = 'data_visible', 'data_full'
        # SET UP FIGURE
        minx = df.e1.min()
        minx *= 1 - minx / abs(minx) * 0.2
        miny = df.e2.min()
        miny *= 1 - miny/abs(miny) * 0.2
        maxx = df.e1.max() * 1.2
        maxy = df.e2.max() * 1.2
        TOOLS = "lasso_select,box_select,hover,crosshair,pan,wheel_zoom,"\
                "box_zoom,reset,tap,help" # poly_select,lasso_select, previewsave

        # SUPLOTS
        p = figure(plot_width=DIM_COMP_W, plot_height=DIM_COMP_H, tools=TOOLS,
                   title=None, logo=None, toolbar_location="above",
                   x_range=Range1d(minx, maxx), y_range=Range1d(miny, maxy),
                   x_axis_type="log", y_axis_type="log"
                   )
        pb = figure(plot_width=DIM_COMP_SM, plot_height=DIM_COMP_H, tools=TOOLS,
                    y_range=p.y_range, x_axis_type="log", y_axis_type="log")
        pa = figure(plot_width=DIM_COMP_W, plot_height=DIM_COMP_SM, tools=TOOLS,
                    x_range=p.x_range, x_axis_type="log", y_axis_type="log")
        pp = figure(plot_width=DIM_COMP_SM, plot_height=DIM_COMP_SM,
                    tools=TOOLS, outline_line_color=None)

        # SPANS
        p.add_layout(plot_fns.get_span(1, 'height'))
        p.add_layout(plot_fns.get_span(1, 'width'))
        pa.add_layout(plot_fns.get_span(1, 'height'))
        pb.add_layout(plot_fns.get_span(1, 'width'))

        # STYLE
        for ax in [p, pa, pb]:
            ax.grid.visible = False
            ax.outline_line_width = 2
            ax.background_fill_color = 'whitesmoke'
        for ax in [pa, pb]:
            ax.xaxis.visible = False
            ax.yaxis.visible = False

        pa.title.text = xlabel
        pb.title.text = ylabel
        pa.title_location, pa.title.align = 'below', 'center'
        pb.title_location, pb.title.align = 'left', 'center'

        # WIDGETS
        q_input = TextInput(value='', title="P* cutoff",
                            placeholder='e.g. 0.05')
        gene_input = TextInput(value='', title="Gene list",
                               placeholder='e.g. TP53,BRAF')
        radio_include = RadioGroup(labels=["Include", "Exclude"], active=0)
        widgets = widgetbox(q_input, gene_input, radio_include, width=200,
                            css_classes=['widgets_sg'])

        grid = gridplot([[pb, p, widgets],
                         [Spacer(width=DIM_COMP_SM), pa, Spacer()]],
                        sizing_mode='fixed')

        cb_inclusion = CustomJS(args=dict(genes=gene_input), code="""
            var gene_str = genes.value
            if (!gene_str)
                return;
            var include = cb_obj.active == 0 ? true : false
            selectPathwaysByGenes(gene_str, include);
            """)
        cb_genes = CustomJS(args=dict(radio=radio_include), code="""
            var gene_str = cb_obj.value
            if (!gene_str)
                return;
            var include = radio.active == 0 ? true : false
            selectPathwaysByGenes(gene_str, include);
            """)
        radio_include.js_on_change('active', cb_inclusion)
        gene_input.js_on_change('value', cb_genes)

        # SCATTER
        p.circle("e1", "e2", source=source, **SCATTER_KW)
        pa.circle('e1_only', 1, source=source, **SCATTER_KW)
        pb.circle(1, 'e2_only', source=source, **SCATTER_KW)

        # HOVER
        for hover in grid.select(dict(type=HoverTool)):
            hover.tooltips = OrderedDict([
                ("name", "@pname"),
                ("effects", "(@e1, @e2)"),
                ("P*", ("(@q1, @q2)"))
            ])

        # ADD Q FILTERING CALLBACK
        callback = CustomJS(args=dict(source=source, full=source_full), code="""
            // get old selection indices, if any
            var prv_selected = source.selected['1d'].indices;
            var prv_select_full = []
            for(var i=0; i<prv_selected.length; i++){
                prv_select_full.push(scatter_array[prv_selected[i]])
            }
            var new_selected = []
            var q_val = cb_obj.value;
            if(q_val == '')
                q_val = 1
            var fullset = full.data;
            var n_total = fullset['e1'].length;
            // Convert float64arrays to array
            var col_names = %s ;
            col_names.forEach(function(col_name){
                source.data[col_name] = [].slice.call(source.data[col_name])
                source.data[col_name].length = 0
            })
            scatter_array.length = 0;
            var j = -1;  // new glyph indices
            for (i = 0; i < n_total; i++) {
                this_q1 = fullset['q1'][i];
                this_q2 = fullset['q2'][i];
                if(this_q1 <= q_val || this_q2 <= q_val){
                    j++; // preserve previous selection if still visible
                    col_names.forEach(function(col){
                        source.data[col].push(fullset[col][i]);
                    })
                    scatter_array.push(i)
                    if($.inArray(i, prv_select_full) > -1){
                        new_selected.push(j);
                    }
                }
            }
            source.selected['1d'].indices = new_selected;
            source.trigger('change');
            updateIfSelectionChange_afterWait();
            """ % columns)

        q_input.js_on_change('value', callback)
        script, div = plot_fns.get_bokeh_components(grid)

        proj_dir_a = naming_rules.get_project_folder(current_proj_a)
        proj_dir_b = naming_rules.get_project_folder(current_proj_b)
        if os.path.exists(os.path.join(proj_dir_a, 'matrix_svg_cnv')) and \
                os.path.exists(os.path.join(proj_dir_b, 'matrix_svg_cnv')):
            has_cnv = True
        else:
            has_cnv = False

    else:  # not enough projects yet!
        flash("Two completed projects are required for a comparison.",
              "warning")
        return redirect(url_for('.index'))

    return render_template('pway/compare.html',
                           current_projs=[current_proj_a, current_proj_b],
                           inds_use=[inds1, inds2],
                           has_cnv=has_cnv,
                           js_name_a=js_name1,
                           js_name_b=js_name2,
                           projects=upload_list,
                           bokeh_script=script,
                           bokeh_div=div, include_genes=include,
                           resources=plot_fns.resources)
Example #2
0
def html_postages(coord=None, idx=None, veto=None, info=None, layer_list=None, BoxSize=40):


    plots = {}
    sources = []
    layers = []

    RA, DEC = coord[0], coord[1]
    scale_unit='pixscale'
    scale=0.262
    boxsize = BoxSize #2*m*radius*3600
    radius = BoxSize/(2 * 3600)
    size = int(round(boxsize/scale))
    figsize = int(128)
    #print('BoxSize', boxsize)
    #print('Size', size)

    idx_list = idx #random.sample(list(idx), rows*cols)

    if info is None:
        info = {'RA':RA, 'DEC':DEC}

    if veto is None:
        veto = {'all':np.ones_like(RA, dtype=bool)}

    if layer_list is None:

        layer_list = ['dr9f-south', 'dr9f-south-model', 'dr9f-south-resid', 'dr9g-south', 'dr9g-south-model', 'dr9g-south-resid',
                 'dr9f-north', 'dr9f-north-model', 'dr9f-north-resid', 'dr9g-north', 'dr9g-north-model', 'dr9g-north-resid']


    for idx in idx_list:

        RAidx = RA[idx]
        DECidx = DEC[idx]

        ramin, ramax = RAidx-radius, RAidx+radius
        decmin, decmax = DECidx-radius, DECidx+radius
        dra = (ramax - ramin)/40
        ddec = (decmax - decmin)/40
        mask = (RA > ramin + dra) & (RA < ramax - dra) & (DEC > decmin + ddec) & (DEC < decmax - ddec)

        TOOLTIPS = []

        for key in info.keys():
            TOOLTIPS.append((key, '@'+key))

        p = figure(plot_width=2*figsize, plot_height=2*figsize, tooltips=TOOLTIPS, tools="tap, save, zoom_in, zoom_out, crosshair")
        p.axis.visible = False
        p.toolbar.logo = None
        p.toolbar_location = None
        #p.min_border = 0

        layers2 = []
        for layer in layer_list:

            source='https://www.legacysurvey.org/viewer-dev/jpeg-cutout/?ra=%.12f&dec=%.12f&%s=%g&layer=%s&size=%g' % (RAidx, DECidx, scale_unit, scale, layer, size)
            url='https://www.legacysurvey.org/viewer-dev?ra=%.12f&dec=%.12f&layer=%s&zoom=15' %(RAidx, DECidx, layer)
            imfig_source = ColumnDataSource(data=dict(url=[source], txt=[source]))
            image1 = ImageURL(url="url", x=0, y=1, w=size, h=size, anchor='bottom_left')
            img_source = p.add_glyph(imfig_source, image1)

            layers2.append(img_source)

        taptool = p.select(type=TapTool)
        taptool.callback = OpenURL(url=url)

        colors = ['green', 'red', 'blue', 'cyan', 'yellow']
        circle_i = []
        for color, key, val in zip(colors, veto.keys(), veto.values()):

            ravpix, decvpix = coordtopix(center=[RAidx, DECidx], coord=[RA[(mask) & (val)], DEC[(mask) & (val)]], size=size, scale=scale)

            data = {}
            data['x'] = ravpix
            data['y'] = decvpix
            for info_key, info_val in zip(info.keys(), info.values()):
                if isinstance(info_val[0], (bytes, bytearray)):
                    data[info_key] = np.array(info_val)[(mask) & (val)].astype('U13')
                else:
                    data[info_key] = np.array(info_val)[(mask) & (val)]

            sourceCirc = ColumnDataSource(data=data)

            circle = p.circle('x', 'y', source=sourceCirc, size=15, fill_color=None, line_color=color, line_width=3)
            circle_i.append(circle)

        lineh = Span(location=size/2, dimension='height', line_color='white', line_dash='solid', line_width=1)
        linew = Span(location=size/2, dimension='width', line_color='white', line_dash='solid', line_width=1)

        p.add_layout(lineh)
        p.add_layout(linew)
        p.background_fill_color = "black"
        #p.outline_line_width = 15
        #p.outline_line_alpha = 0.7

        p.xgrid.grid_line_color = None
        p.ygrid.grid_line_color = None

        plots[str(idx)] = p

        sources.append(circle_i)
        layers.append(layers2)


    checkbox = CheckboxGroup(labels=list(veto.keys()), active=list(np.arange(len(veto))))
    iterable = [elem for part in [[('_'.join(['line',str(figid),str(lineid)]),line) for lineid,line in enumerate(elem)] for figid,elem in enumerate(sources)] for elem in part]
    checkbox_code = ''.join([elem[0]+'.visible=checkbox.active.includes('+elem[0].split('_')[-1]+');' for elem in iterable])
    callback = CustomJS(args={key:value for key,value in iterable+[('checkbox',checkbox)]}, code=checkbox_code)

    # print('===== plots ======')
    # print(checkbox_code)
    # print('====')
    # print({key:value for key,value in iterable+[('checkbox',checkbox)]})

    checkbox.js_on_click(callback)

    #script, div = components(plots)
    #print(div)

    radio = RadioGroup(labels=layer_list, active=len(layer_list)-1)
    iterable2 = [elem for part in [[('_'.join(['line',str(figid),str(lineid)]),line) for lineid,line in enumerate(elem)] for figid,elem in enumerate(layers)] for elem in part]
    #
    N = len(layer_list)
    text = []
    for elem in iterable2[::N]:
        for n in range(N):
            text.append('%s%s.visible=false;' %(elem[0][:-1], str(n)))
        for n in range(N):
            if n == 0: text.append('if (cb_obj.active == 0) {%s%s.visible = true;}' %(elem[0][:-1], str(0)))
            if n != 0: text.append('else if (cb_obj.active == %s) {%s%s.visible = true;}' %(str(n), elem[0][:-1], str(n)))

    radiogroup_code = ''.join(text)

    callback2 = CustomJS(args={key:value for key,value in iterable2+[('radio',radio)]}, code=radiogroup_code)
    radio.js_on_change('active', callback2)


    # for key,val in zip(plots.keys(), plots.values()):
    #     print(key, '\t', val)

    #script, div = components(plots)
    #controls = WidgetBox(radio, checkbox)
    #plots['controls'] = components(radio)
    #script_2, div_2 = components(controls)

    #print('===== plots ======')
    plots['checkbox'] = checkbox
    plots['radio'] = radio

    return components(plots)
        
        }
        
        TSR=(95*Sytexp-Sexp*Syt)/Math.sqrt(95*Sytsq-Syt*Syt)/Math.sqrt(95*Sexpsq-Sexp*Sexp)
        
        TSR=Math.round(TSR*100)/100
        
        corlabTS.text='TS R='.concat(TSR.toString())

        source.trigger('change');
    """)


cbox.js_on_change('active', cb)
slider.js_on_change('value', cb_slider)
rb_group.js_on_change('active', cb_ff)
rb_group2.js_on_change('active', cb_struct)
div = Div(text="""<b>Figure: Comparison of H-SASA profiles calculated with different parameters with experimental cleavage frequencies. Top strand (TS) of <i>S. cerevisiae</i> centromeric nucleosome with 601TA DNA sequence.</b>
<br><br>
This interactive plot allows to explore dependence of H-SASA profiles on different paramters. Correlation coefficient is interactively displayed in the bottom left corner.
Use contols above to choose between following paramters:<br><br>
<b>Structure used for calculations</b>: X-H nuclear - orginal X-ray derived structure, hydrogen atoms added via REDUCE program with nuclear distances for X-H bond length;
X-H electron - original X-ray derived structure, hydrogen atoms added via REDUCE program with electron cloud distances for X-H bond length;
MD average - average profile for 50 frames spaced 1 ns apart from molecular dynamics simulations with CHARMM36 force field with NAMD.
<br><br>
<b>Radii of atoms used for SASA calculations</b>: FreeSASA Default - default radii in FreeSASA program; CHARMM36-rmin - van der Waals radii (Rmin paramter) of atoms as defined by CHARMM36 force field;
AMBER10-rmin - van der Waals radii (Rmin paramter) of atoms as defined by AMBER10 force field.
<br><br>
<b>Contributions of deoxyribose hydrogen atoms</b>: SASA of deoxyribose hydrogen atoms selected will be included in calculation of H-SASA profile.
<br><br>
<b>Probe radius</b>: radius of the probe sphere used to calculate SASA, 1.4 A is a default for SASA calculations, OH-radical size is around 1.2 A, higher values are more sensitive to the geometry of the complex.