File Coverage

blib/lib/Bio/Phylo/Unparsers/Figtree.pm
Criterion Covered Total %
statement 46 48 95.8
branch 6 10 60.0
condition n/a
subroutine 8 8 100.0
pod n/a
total 60 66 90.9


line stmt bran cond sub pod time code
1             package Bio::Phylo::Unparsers::Figtree;
2 1     1   13 use strict;
  1         7  
  1         88  
3 1     1   11 use base 'Bio::Phylo::Unparsers::Nexus';
  1         10  
  1         558  
4 1     1   12 use Bio::Phylo::Util::Logger ':levels';
  1         5  
  1         165  
5 1     1   373 use Bio::Phylo::Util::Exceptions 'throw';
  1         5  
  1         71  
6 1     1   10 use Bio::Phylo::Util::CONSTANT qw':objecttypes :namespaces';
  1         155  
  1         453  
7 1     1   9 use Data::Dumper;
  1         3  
  1         667  
8              
9             my $log = Bio::Phylo::Util::Logger->new;
10             my $ns = _NS_FIGTREE_;
11             my $pre = 'fig';
12              
13             =head1 NAME
14              
15             Bio::Phylo::Unparsers::Figtree - Serializer used by Bio::Phylo::IO, no serviceable parts inside
16              
17             =head1 DESCRIPTION
18              
19             This module turns objects into a nexus-formatted string that uses additional
20             syntax for Figtree. It is called by the L facade, don't call it
21             directly. You can pass the following additional arguments to the unparse call:
22            
23             =begin comment
24              
25             Type : Wrapper
26             Title : _to_string($obj)
27             Usage : $figtree->_to_string($obj);
28             Function: Stringifies an object into
29             a nexus/figtree formatted string.
30             Alias :
31             Returns : SCALAR
32             Args : Bio::Phylo::*
33              
34             =end comment
35              
36             =cut
37              
38             sub _to_string {
39 1     1   4 my $self = shift;
40 1         18 $self->{'FOREST_ARGS'} = {
41             '-nodelabels' => \&_figtree_handler,
42             '-figtree' => 1,
43             };
44 1         9 return $self->SUPER::_to_string(@_);
45             }
46              
47             sub _figtree_handler {
48              
49             # node object, translation table ID, if any
50 35     35   114 my ( $node, $id ) = @_;
51              
52             # fetch Meta objects, filter out the ones that are _NS_FIGTREE_,
53             # turn them into a hash without the fig prefix
54 35         107 my @meta = @{ $node->get_meta };
  35         140  
55 637         1870 my %meta = map { $_->get_predicate_local => $_->get_object }
56 35         109 grep { $_->get_predicate_namespace eq $ns } @meta;
  637         1360  
57 35         275 $log->debug( Dumper(\%meta) );
58            
59             # there can be separate annotations that are _min and _max for
60             # the same variable name stem. We combine these into a range
61             # between curly braces. Also add % percentage symbol for 95%
62             # HPD ranges - the % symbol is disallowed in CURIEs, hence we
63             # have to bring it back here.
64 35         118 my %merged;
65 35         162 KEY: for my $key ( keys %meta ) {
66 637 100       2094 if ( $key =~ /^(.+?)_min$/ ) {
    100          
67 206         450 my $stem = $1;
68 206         324 my $max_key = $stem . '_max';
69 206         433 $stem =~ s/95/95%/;
70 206         811 $merged{$stem} = '{'.$meta{$key}.','.$meta{$max_key}.'}';
71             }
72             elsif ( $key =~ /^(.+?)_max$/ ) {
73 206         330 next KEY;
74             }
75             else {
76 225         314 $key =~ s/95/95%/;
77 225         384 $merged{$key} = $meta{$key};
78             }
79             }
80            
81             # create the concatenated annotation string
82 35         192 my $anno = '[&' . join( ',',map { $_.'='.$merged{$_} } keys %merged ) . ']';
  431         979  
83            
84             # construct the name:
85 35         119 my $name;
86            
87             # case 1 - a translation table index was provided, this now replaces the name
88 35 50       101 if ( defined $id ) {
    0          
89 35         89 $name = $id;
90             }
91            
92             # case 2 - no translation table index, use the node name
93             elsif ( defined $node->get_name ) {
94 0         0 $name = $node->get_name;
95             }
96            
97             # case 3 - use the empty string, to avoid uninitialized warnings.
98             else {
99 0         0 $name = '';
100             }
101            
102             # append the annotation string, if we have it
103 35 50       155 my $annotated = $anno ne '[&]' ? $name . $anno : $name;
104 35         133 $log->debug($annotated);
105 35         315 return $annotated;
106             }
107              
108             # podinherit_insert_token
109              
110             =head1 SEE ALSO
111              
112             There is a mailing list at L
113             for any user or developer questions and discussions.
114              
115             =over
116              
117             =item L
118              
119             The nexus serializer is called by the L object.
120              
121             =item L
122              
123             Also see the manual: L and L.
124              
125             =back
126              
127             =head1 CITATION
128              
129             If you use Bio::Phylo in published research, please cite it:
130              
131             B, B, B, B
132             and B, 2011. Bio::Phylo - phyloinformatic analysis using Perl.
133             I B<12>:63.
134             L
135              
136             =cut
137              
138             1;