# Copyright 2003-2008 by Leighton Pritchard. All rights reserved. # This code is part of the Biopython distribution and governed by its # license. Please see the LICENSE file that should have been included # as part of this package. # # Contact: Leighton Pritchard, Scottish Crop Research Institute, # Invergowrie, Dundee, Scotland, DD2 5DA, UK # L.Pritchard@scri.ac.uk ################################################################################ """ Track module Provides: o Track - Container for a single track on the diagram, containing FeatureSet and GraphSet objects For drawing capabilities, this module uses reportlab to draw and write the diagram: http://www.reportlab.com For dealing with biological information, the package expects BioPython objects: http://www.biopython.org """ # ReportLab imports from reportlab.lib import colors # GenomeDiagram imports from _FeatureSet import FeatureSet from _GraphSet import GraphSet class Track: """ Track Provides: Methods: o __init__(self, name=None, height=1, hide=0, greytrack=0, greytrack_labels=5, greytrack_fontsize=8, greytrack_font='Helvetica', greytrack_font_rotation=0, greytrack_fontcolor = colors.Color(0.6, 0.6, 0.6), scale=1, scale_color=colors.black, scale_font='Helvetica', scale_fontsize=6, scale_fontangle=45, scale_largeticks=0.5, scale_ticks=1, scale_smallticks=0.3, scale_largetick_interval=1e6, scale_smalltick_interval=1e4, scale_largetick_labels=1, scale_smalltick_labels=0) Called on instantiation o add_set(self, set) Add a FeatureSet or GraphSet to the diagram o del_set(self, set_id) Delete a FeatureSet or GraphSet from the diagram o get_sets(self) Returns a list of the sets in the track o get_ids(self) Returns a list of the ids for sets in the track o range(self) Returns the base/position range covered by the data in the track o to_string(self, verbose=0) Returns a string describing the data in the track o __getitem__(self, key) Returns the set with the passed id o __str__(self) Returns a formatted string describing the track Attributes: o height Int describing the relative height to other trackscale_fontsizes in the diagram o name String describing the track o hide Boolean, 0 if the track is not to be drawn o greytrack Boolean, 1 if a grey background to the track is to be drawn o greytrack_labels Int describing how many track-identifying labels should be placed on the track at regular intervals o greytrack_font String describing the font to use for the greytrack labels o greytrack_fontsize Int describing the font size to display the labels on the grey track o greytrack_font_rotation Int describing the angle through which to rotate the grey track labels o greytrack_font_color colors.Color describing the color to draw the grey track labels o scale Boolean, 1 if a scale is to be drawn on the track o scale_format String, defaults to None, when scale values are written as numerals. Setting this to 'SInt' invokes SI unit-like multiples, such as Mbp, Kbp and so on. o scale_color colors.Color to draw the elemnts of the scale o scale_font String describing the font to use for the scale labels o scale_fontsize Int describing the size of the scale label font o scale_fontangle Int describing the angle at which to draw the scale labels (linear only) o scale_ticks Boolean, 1 if ticks should be drawn at all on the scale o scale_largeticks Float (0->1) describing the height of large scale ticks relative to the track height. o scale_smallticks Float (0->1) describing the height of large scale ticks relative to the track height. o scale_largetick_interval Int, describing the number of bases that should separate large ticks o scale_smalltick_interval Int, describing the number of bases that should separate small ticks o scale_largetick_labels Boolean describing whether position labels should be written over large ticks o scale_smalltick_labels Boolean describing whether position labels should be written over small ticks o axis_labels Boolean describing whether the value labels should be placed on the Y axes """ def __init__(self, name=None, height=1, hide=0, greytrack=0, greytrack_labels=5, greytrack_fontsize=8, greytrack_font='Helvetica', greytrack_font_rotation=0, greytrack_font_color = colors.Color(0.6, 0.6, 0.6), scale=1, scale_format=None, scale_color=colors.black, scale_font='Helvetica', scale_fontsize=6, scale_fontangle=45, scale_largeticks=0.5, scale_ticks=1, scale_smallticks=0.3, scale_largetick_interval=1e6, scale_smalltick_interval=1e4, scale_largetick_labels=1, scale_smalltick_labels=0, axis_labels=1, greytrack_font_colour = None, scale_colour=None): """ __init__(self, name=None, height=1) o height Int describing the relative height to other tracks in the diagram o name String describing the track o hide Boolean, 0 if the track is not to be drawn o greytrack Boolean, 1 if a grey background to the track is to be drawn o greytrack_labels Int describing how many track-identifying labels should be placed on the track at regular intervals o greytrack_font String describing the font to use for the greytrack labels o greytrack_fontsize Int describing the font size to display the labels on the grey track o greytrack_font_rotation Int describing the angle through which to rotate the grey track labels o greytrack_font_color colors.Color describing the color to draw the grey track labels (overridden by backwards compatible argument with UK spelling, colour). o scale Boolean, 1 if a scale is to be drawn on the track o scale_color colors.Color to draw the elemnts of the scale (overridden by backwards compatible argument with UK spelling, colour). o scale_font String describing the font to use for the scale labels o scale_fontsize Int describing the size of the scale label font o scale_fontangle Int describing the angle at which to draw the scale labels (linear only) o scale_ticks Boolean, 1 if ticks should be drawn at all on the scale o scale_largeticks Float (0->1) describing the height of large scale ticks relative to the track height. o scale_smallticks Float (0->1) describing the height of large scale ticks relative to the track height. o scale_largetick_interval Int, describing the number of bases that should separate large ticks o scale_smalltick_interval Int, describing the number of bases that should separate small ticks o scale_largetick_labels Boolean describing whether position labels should be written over large ticks o scale_smalltick_labels Boolean describing whether position labels should be written over small ticks o name String to help identify the track o height Relative height to draw the track o axis_labels Boolean describing whether the value labels should be placed on the Y axes """ #Let the UK spelling (colour) override the USA spelling (color) if greytrack_font_colour is not None: greytrack_font_color = greytrack_font_colour if scale_colour is not None: scale_color = scale_colour self._next_id = 0 # This will count sets as they are added to the track self._sets = {} # Holds sets, keyed by unique ID # Assign attribute values from instantiation self.height = height if name is not None: self.name = str(name) else: self.name = "Track" self.hide = hide # Attributes for the grey track background and labels self.greytrack = greytrack self.greytrack_labels = greytrack_labels self.greytrack_fontsize = greytrack_fontsize self.greytrack_font = greytrack_font self.greytrack_font_rotation = greytrack_font_rotation self.greytrack_fontcolor = greytrack_font_color # Attributes for the track scale self.scale = scale self.scale_format = scale_format self.scale_color = scale_color self.scale_font = scale_font self.scale_fontsize = scale_fontsize self.scale_fontangle = scale_fontangle self.scale_ticks = scale_ticks self.scale_largeticks = scale_largeticks self.scale_smallticks = scale_smallticks self.scale_largetick_interval = scale_largetick_interval self.scale_smalltick_interval = scale_smalltick_interval self.scale_largetick_labels = scale_largetick_labels self.scale_smalltick_labels = scale_smalltick_labels self.axis_labels = axis_labels def add_set(self, set): """ add_set(self, set) o set A FeatureSet or GraphSet object Add a preexisting FeatureSet or GraphSet object to the track """ set.id = self._next_id # Assign unique id to set set.parent = self # Make set's parent this track self._sets[self._next_id] = set # Add set, keyed by unique id self._next_id += 1 # Increment unique set ids def new_set(self, type='feature', **args): """ new_set(self, type='feature') -> FeatureSet or GraphSet Create a new FeatureSet or GraphSet object, add it to the track, and return for user manipulation """ type_dict = {'feature': FeatureSet, 'graph': GraphSet } set = type_dict[type]() for key in args: setattr(set, key, args[key]) set.id = self._next_id # Assign unique id to set set.parent = self # Make set's parent this track self._sets[self._next_id] = set # Add set, keyed by unique id self._next_id += 1 # Increment unique set ids return set def del_set(self, set_id): """ del_set(self, set_id) o set_id The unique id for the set in this track Remove the set with the passed id from the track """ del self._sets[set_id] def get_sets(self): """ get_sets(self) -> FeatureSet or GraphSet Return the sets contained in this track """ return self._sets.values() def get_ids(self): """ get_ids(self) -> [int, int, ...] Return the ids of all sets contained in this track """ return self._sets.keys() def range(self): """ range(self) -> (int, int) Returns the lowest and highest base (or mark) numbers as a tuple """ lows, highs = [], [] # Holds set of low and high values from sets for set in self._sets.values(): low, high = set.range() # Get each set range lows.append(low) highs.append(high) return (min(lows), max(highs)) # Return lowest and highest values def to_string(self, verbose=0): """ to_string(self, verbose=0) -> "" o verbose Boolean indicating whether a short or complete account of the track is required Returns a formatted string with information about the track """ if not verbose: # Return the short description return "%s" % self # Use __str__ method instead else: # Return the long desription outstr = ["\n<%s: %s>" % (self.__class__, self.name)] outstr.append("%d sets" % len(self._sets)) for key in self._sets: outstr.append("set: %s" % self._sets[key]) return "\n".join(outstr) def __getitem__(self, key): """ __getitem__(self, key) -> int o key The id of a set in the track Return the set with the passed id """ return self._sets[key] def __str__(self): """ __str__(self) -> "" Returns a formatted string with information about the Track """ outstr = ["\n<%s: %s>" % (self.__class__, self.name)] outstr.append("%d sets" % len(self._sets)) return "\n".join(outstr) ################################################################################ # RUN AS SCRIPT ################################################################################ if __name__ == '__main__': # test code from Bio import GenBank from Bio.SeqFeature import SeqFeature from _FeatureSet import FeatureSet from _GraphSet import GraphSet from random import normalvariate parser = GenBank.FeatureParser() fhandle = open('/data/genomes/Bacteria/Nanoarchaeum_equitans/NC_005213.gbk', 'r') genbank_entry = parser.parse(fhandle) fhandle.close() gdfs1 = FeatureSet(0, 'Nanoarchaeum equitans CDS - CDS') gdfs2 = FeatureSet(1, 'Nanoarchaeum equitans CDS - gene') for feature in genbank_entry.features: if feature.type == 'CDS': gdfs1.add_feature(feature) if feature.type == 'gene': gdfs2.add_feature(feature) gdt = Track() gdt.add_set(gdfs1) gdt.add_set(gdfs2) graphdata = [] for pos in xrange(1, len(genbank_entry.seq), 1000): graphdata.append((pos, normalvariate(0.5, 0.1))) gdgs = GraphSet(2, 'test data') gdgs.add_graph(graphdata, 'Test Data') gdt.add_set(gdgs) print gdt.get_ids() sets = gdt.get_sets() for set in sets: print set print gdt.get_element_limits()