<commit_before>package Bio::EnsEMBL::GlyphSet::_das;

use strict;
use base qw(Bio::EnsEMBL::GlyphSet_generic);

use Bio::EnsEMBL::ExternalData::DAS::Stylesheet;

use POSIX qw(floor ceil);
use Data::Dumper;

sub features       { 
  my $self = shift;
  
  ## Fetch all the das features...
  unless( $self->cache('das_features') ) {
    # Query by slice:
    $self->cache('das_features', $self->cache('das_coord')->fetch_Features( $self->{'container'}, 'maxbins' => $self->image_width )||{} );
  }
  
  my $data = $self->cache('das_features');
  
  my @logic_names =  @{ $self->my_config('logicnames') };
  my $res = {};

  my %feature_styles = ();
  my %group_styles   = ();
  my $min_score      = 0;
  my $max_score      = 0;
  my $max_height     = 0;
  my %groups         = ();  
  my %orientations   = ();
  my @urls           = ();
  my @errors         = ();

  my $c_f=0;
  my $c_g=0;
  for my $logic_name ( @logic_names ) {
    local $Data::Dumper::Indent = 1;    

    my $stylesheet = $data->{ $logic_name }{ 'stylesheet' }{ 'object' }
      || $Bio::EnsEMBL::ExternalData::DAS::Stylesheet::DEFAULT_STYLESHEET;
    warn Data::Dumper::Dumper( $stylesheet );
    
    for my $segment ( keys %{ $data->{ $logic_name }{ 'features' } } ) {
      
      my $f_data = $data->{ $logic_name }{ 'features' }{ $segment };
      push @urls,   $f_data->{ 'url' };
      push @errors, $f_data->{'error'};
      
      for my $f ( @{ $f_data->{'objects'} } ) {
        
        # Skip nonpositional features
        $f->start || $f->end || next;
        
      my $style_key = $f->type_category."\t".$f->type_id;
      unless( exists $feature_styles{$logic_name}{ $style_key } ) {
        my $st = $stylesheet->find_feature_glyph( $f->type_category, $f->type_id, 'default' );
        $feature_styles{$logic_name}{$style_key} = {
          'style'      => $st,
          'use_score'  => ($st->{'symbol'} =~ /^(histogram|tiling|lineplot|gradient)/i ? 1 : 0)
        };
        $max_height = $st->{height} if $st->{height} > $max_height;
      };
      my $fs = $feature_styles{$logic_name}{$style_key};
      next if $fs->{'style'}{'symbol'} eq 'hidden';  ## STYLE MEANS NOT DRAWN!
      $c_f ++;
      if( $fs->{'use_score'} ) { ## These are the score based symbols
        $min_score = $f->score if $f->score < $min_score;
        $max_score = $f->score if $f->score > $max_score;
      }
## Loop through each group so we can merge this into "group-based clusters"
      my $st = $f->seq_region_strand || 0;
      $orientations{ $st }++;
      if( @{$f->groups} ) { ## Feature has groups so use them...
        foreach( @{$f->groups} ) {
          my $g  = $_->{'group_id'};
          my $ty = $_->{'group_type'};
          my $gs = $group_styles{$logic_name}{ $ty } ||= { 'style' => $stylesheet->find_group_glyph( $ty, 'default' ) };
          if( exists $groups{$logic_name}{$g}{$st} ) {
            my $t = $groups{$logic_name}{$g}{$st};
            push @{ $t->{'features'}{$style_key} }, $f;
            $t->{'start'} = $f->start if $f->start < $t->{'start'};
            $t->{'end'}   = $f->end   if $f->end   > $t->{'end'};
            $t->{'count'} ++;
          } else {
            $c_g++;
            $groups{$logic_name}{$g}{$st} = {
              'count'   => 1,
              'type'    => $ty,
              'id'      => $g,
              'label'   => $_->{'group_label'},
              'notes'   => $_->{'notes'},
              'links'   => $_->{'links'},
              'targets' => $_->{'target'},
              'features'=>{$style_key=>[$f]},'start'=>$f->start,'end'=>$f->end
            };
          }
        }
      } else { ## Feature doesn't have groups so fake it with the feature id as group id!
        my $g     = ( $fs->{'use_score'} || $fs->{'style'}{'bump'} eq '0' ) ? 'default' : $f->display_id;      ## If histogram/un-bumped
        my $label = ( $fs->{'use_score'} || $fs->{'style'}{'bump'} eq '0' ) ? ''        : $f->display_label;   ## If histogram/un-bumped
        my $ty = $f->type_id;       # & the feature type
        my $gs = $group_styles{$logic_name}{ $ty } ||= { 'style' => $stylesheet->find_group_glyph( $ty, 'default' ) };
        if( exists $groups{$logic_name}{$g}{$st} ) {
## Ignore all subsequent notes, links and targets, probably should merge arrays somehow....
          my $t = $groups{$logic_name}{$g}{$st};
          push @{ $t->{'features'}{$style_key} }, $f;
          $t->{'start'} = $f->start if $f->start < $t->{'start'};
          $t->{'end'}   = $f->end   if $f->end   > $t->{'end'};
          $t->{'count'} ++;
        } else {
          $c_g++;
          $groups{$logic_name}{$g}{$st} = {
            'count'   => 1,
            'type'    => $ty,
            'id'      => $g,
            'label'   => $label,
            'notes'   => $f->{'note'},   ## Push the features notes/links and targets on!
            'links'   => $f->{'link'},
            'targets' => $f->{'target'},
            'features'=>{$style_key=>[$f]},'start'=>$f->start,'end'=>$f->end
          };
        }
      }
    }
    
    }
## If we used a guessed max/min make it significant to two figures!!
    if( $max_score == $min_score ) { ## If we have all "0" data adjust so we have a range
      $max_score =  0.1;
      $min_score = -0.1;
    } else {
      my $base = 10**POSIX::ceil(log($max_score-$min_score)/log(10))/100;
      $min_score = POSIX::floor( $min_score / $base ) * $base;
      $max_score = POSIX::ceil(  $max_score / $base ) * $base;
    }<commit_msg>Fixed indent<commit_after>package Bio::EnsEMBL::GlyphSet::_das;

use strict;
use base qw(Bio::EnsEMBL::GlyphSet_generic);

use Bio::EnsEMBL::ExternalData::DAS::Stylesheet;

use POSIX qw(floor ceil);
use Data::Dumper;

sub features       { 
  my $self = shift;
  
  ## Fetch all the das features...
  unless( $self->cache('das_features') ) {
    # Query by slice:
    $self->cache('das_features', $self->cache('das_coord')->fetch_Features( $self->{'container'}, 'maxbins' => $self->image_width )||{} );
  }
  
  my $data = $self->cache('das_features');
  
  my @logic_names =  @{ $self->my_config('logicnames') };
  my $res = {};

  my %feature_styles = ();
  my %group_styles   = ();
  my $min_score      = 0;
  my $max_score      = 0;
  my $max_height     = 0;
  my %groups         = ();  
  my %orientations   = ();
  my @urls           = ();
  my @errors         = ();

  my $c_f=0;
  my $c_g=0;
  for my $logic_name ( @logic_names ) {
    local $Data::Dumper::Indent = 1;    

    my $stylesheet = $data->{ $logic_name }{ 'stylesheet' }{ 'object' }
      || $Bio::EnsEMBL::ExternalData::DAS::Stylesheet::DEFAULT_STYLESHEET;
    warn Data::Dumper::Dumper( $stylesheet );
    
    for my $segment ( keys %{ $data->{ $logic_name }{ 'features' } } ) {
      
      my $f_data = $data->{ $logic_name }{ 'features' }{ $segment };
      push @urls,   $f_data->{ 'url' };
      push @errors, $f_data->{'error'};
      
      for my $f ( @{ $f_data->{'objects'} } ) {
        
        # Skip nonpositional features
        $f->start || $f->end || next;
        
        my $style_key = $f->type_category."\t".$f->type_id;
        unless( exists $feature_styles{$logic_name}{ $style_key } ) {
          my $st = $stylesheet->find_feature_glyph( $f->type_category, $f->type_id, 'default' );
          $feature_styles{$logic_name}{$style_key} = {
            'style'      => $st,
            'use_score'  => ($st->{'symbol'} =~ /^(histogram|tiling|lineplot|gradient)/i ? 1 : 0)
          };
          $max_height = $st->{height} if $st->{height} > $max_height;
        };
        my $fs = $feature_styles{$logic_name}{$style_key};
        next if $fs->{'style'}{'symbol'} eq 'hidden';  ## STYLE MEANS NOT DRAWN!
        $c_f ++;
        if( $fs->{'use_score'} ) { ## These are the score based symbols
          $min_score = $f->score if $f->score < $min_score;
          $max_score = $f->score if $f->score > $max_score;
        }
  ## Loop through each group so we can merge this into "group-based clusters"
        my $st = $f->seq_region_strand || 0;
        $orientations{ $st }++;
        if( @{$f->groups} ) { ## Feature has groups so use them...
          foreach( @{$f->groups} ) {
            my $g  = $_->{'group_id'};
            my $ty = $_->{'group_type'};
            my $gs = $group_styles{$logic_name}{ $ty } ||= { 'style' => $stylesheet->find_group_glyph( $ty, 'default' ) };
            if( exists $groups{$logic_name}{$g}{$st} ) {
              my $t = $groups{$logic_name}{$g}{$st};
              push @{ $t->{'features'}{$style_key} }, $f;
              $t->{'start'} = $f->start if $f->start < $t->{'start'};
              $t->{'end'}   = $f->end   if $f->end   > $t->{'end'};
              $t->{'count'} ++;
            } else {
              $c_g++;
              $groups{$logic_name}{$g}{$st} = {
                'count'   => 1,
                'type'    => $ty,
                'id'      => $g,
                'label'   => $_->{'group_label'},
                'notes'   => $_->{'notes'},
                'links'   => $_->{'links'},
                'targets' => $_->{'target'},
                'features'=>{$style_key=>[$f]},'start'=>$f->start,'end'=>$f->end
              };
            }
          }
        } else { ## Feature doesn't have groups so fake it with the feature id as group id!
          my $g     = ( $fs->{'use_score'} || $fs->{'style'}{'bump'} eq '0' ) ? 'default' : $f->display_id;      ## If histogram/un-bumped
          my $label = ( $fs->{'use_score'} || $fs->{'style'}{'bump'} eq '0' ) ? ''        : $f->display_label;   ## If histogram/un-bumped
          my $ty = $f->type_id;       # & the feature type
          my $gs = $group_styles{$logic_name}{ $ty } ||= { 'style' => $stylesheet->find_group_glyph( $ty, 'default' ) };
          if( exists $groups{$logic_name}{$g}{$st} ) {
  ## Ignore all subsequent notes, links and targets, probably should merge arrays somehow....
            my $t = $groups{$logic_name}{$g}{$st};
            push @{ $t->{'features'}{$style_key} }, $f;
            $t->{'start'} = $f->start if $f->start < $t->{'start'};
            $t->{'end'}   = $f->end   if $f->end   > $t->{'end'};
            $t->{'count'} ++;
          } else {
            $c_g++;
            $groups{$logic_name}{$g}{$st} = {
              'count'   => 1,
              'type'    => $ty,
              'id'      => $g,
              'label'   => $label,
              'notes'   => $f->{'note'},   ## Push the features notes/links and targets on!
              'links'   => $f->{'link'},
              'targets' => $f->{'target'},
              'features'=>{$style_key=>[$f]},'start'=>$f->start,'end'=>$f->end
            };
          }
        }
      }
    
    }
## If we used a guessed max/min make it significant to two figures!!
    if( $max_score == $min_score ) { ## If we have all "0" data adjust so we have a range
      $max_score =  0.1;
      $min_score = -0.1;
    } else {
      my $base = 10**POSIX::ceil(log($max_score-$min_score)/log(10))/100;
      $min_score = POSIX::floor( $min_score / $base ) * $base;
      $max_score = POSIX::ceil(  $max_score / $base ) * $base;
    }
{'fraction_non_alphanumeric': 0.2111121084283278, 'fraction_numerical': 0.004487927475092002, 'mean_word_length': 2.091564927857936, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 215, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4652271', 'n_tokens_mistral': 4002, 'n_tokens_neox': 3874, 'n_words': 805}