Changeset 5138


Ignore:
Timestamp:
Oct 16, 2009, 2:27:01 PM (12 years ago)
Author:
Nicklas Nordborg
Message:

References #1385 and #1386. Plot functions in experiment explorer

Both types of plots can now be generated and I think the percentile values are correctly calculated.

Location:
trunk
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/clients/web/net/sf/basedb/clients/web/servlet/ExperimentExplorerPlotServlet.java

    r5114 r5138  
    3434import java.util.ArrayList;
    3535import java.util.Collection;
     36import java.util.Collections;
    3637import java.util.HashMap;
    3738import java.util.List;
     
    4041
    4142import javax.imageio.ImageIO;
     43import javax.servlet.ServletConfig;
    4244import javax.servlet.ServletException;
    4345import javax.servlet.http.HttpServlet;
     
    5658import org.jfree.chart.plot.CategoryPlot;
    5759import org.jfree.chart.plot.Plot;
     60import org.jfree.chart.renderer.category.BoxAndWhiskerRenderer;
    5861import org.jfree.chart.renderer.category.LineAndShapeRenderer;
    5962import org.jfree.chart.title.TextTitle;
    6063import org.jfree.data.category.DefaultCategoryDataset;
     64import org.jfree.data.statistics.BoxAndWhiskerItem;
     65import org.jfree.data.statistics.DefaultBoxAndWhiskerCategoryDataset;
    6166
    6267import net.sf.basedb.clients.web.ExperimentExplorer;
     
    8994
    9095/**
    91 
     96  Plot servlet for generating plots from experiment explorer.
     97 
    9298  @author Nicklas
    9399  @version 2.14
     
    98104{
    99105 
     106  private static final long serialVersionUID = -445763412868957935L;
    100107  private int maxWidth = 1000;
    101108  private int maxHeight = 800;
     
    104111  private String defaultFormat = "png";
    105112
     113  @Override
     114  public void init()
     115    throws ServletException
     116  {
     117    ServletConfig cfg = getServletConfig();
     118    maxWidth = Values.getInt(cfg.getInitParameter("maxWidth"), maxWidth);
     119    maxHeight = Values.getInt(cfg.getInitParameter("maxHeight"), maxHeight);
     120    defaultWidth = Values.getInt(cfg.getInitParameter("defaultWidth"), defaultWidth);
     121    defaultHeight = Values.getInt(cfg.getInitParameter("defaultHeight"), defaultHeight);
     122    defaultFormat = Values.getString(cfg.getInitParameter("defaultFormat"), defaultFormat);
     123  }
    106124 
     125  @SuppressWarnings("unchecked")
     126  @Override
    107127  public void doGet(HttpServletRequest request, HttpServletResponse response)
    108128    throws IOException, ServletException
     
    114134    final int reporterIndex = Values.getInt(request.getParameter("reporterIndex"));
    115135    final int positionIndex = Values.getInt(request.getParameter("positionIndex"));
     136    final String plotType = Values.getString(request.getParameter("type"), "line");
    116137   
    117138    // Where to deliver the image
     
    150171    if (yLog && yLabel != null) yLabel = "log2("+yLabel+")";
    151172    final boolean showXLabels = Values.getBoolean(request.getParameter("showXLabels"));
    152     System.out.println("showXLabels=" + showXLabels);
    153 
     173
     174    // Box plot specific parameters
     175    final int annotationTypeId = Values.getInt(request.getParameter("annotationTypeId"));
     176   
    154177    final SessionControl sc = Application.getSessionControl(ID, request.getRemoteAddr());
    155178    DbControl dc = null;
     
    165188        final ExperimentExplorer explorer = ExperimentExplorer.getExplorer(bioAssaySet);
    166189     
    167         // Load bioassay information - make sure each the labels are unique
    168         // and that we can go between label<-->column in both directions
    169         Map<String, Short> labelToColumn = new HashMap<String, Short>();
    170         Map<Short, String> columnToLabel = new HashMap<Short, String>();
    171         for (BioAssay ba : bioAssaySet.getBioAssays().list(dc))
    172         {
    173           String lbl = ba.getName();
    174           short column = ba.getDataCubeColumnNo();
    175           if (labelToColumn.containsKey(lbl))
    176           {
    177             lbl = lbl + "-" + ba.getId();
    178           }
    179           labelToColumn.put(lbl, column);
    180           columnToLabel.put(column, lbl);
    181         }
    182190       
    183         // Load annotation summaries
    184         Set<Integer> annotationTypes = explorer.getAnnotationTypeIds();
    185         List<AnnotationSummary> summaries = new ArrayList<AnnotationSummary>(3);
    186         if (showXLabels && annotationTypes != null && annotationTypes.size() > 0)
    187         {
    188           for (Integer annotationTypeId : annotationTypes)
    189           {
    190             AnnotationType at = AnnotationType.getById(dc, annotationTypeId);
    191             summaries.add(explorer.getAnnotationSummary(dc, at));
    192             if (summaries.size() == 3) break;
    193           }
    194         }
    195        
     191        // Create some common items used for all plot types
     192          NumberAxis valueAxis = new NumberAxis(yLabel);
     193          CategoryAxis categoryAxis = new CategoryAxis();
     194
    196195        // Convert formulas to Expression:s
    197196        Expression y = yFormula == null ? null :
     
    203202        DynamicSpotQuery query = explorer.getSpotQuery(dc, reporterIndex, positionIndex, new ArrayList<TableColumn>());
    204203        query.select(Selects.expression(y, "y"));
    205      
    206         // Load the spot data into the dataset
    207         DefaultCategoryDataset dataset = new DefaultCategoryDataset();
    208         DynamicResultIterator it = query.iterate(dc);
    209         int valueIndex = it.getIndex("y");
    210         int columnIndex = it.getIndex(VirtualColumn.COLUMN.getName());
    211         int posIndex = positionIndex == ExperimentExplorer.SPOT_ALL ?
    212           it.getIndex(VirtualColumn.POSITION.getName()) : 0;
    213         while (it.hasNext())
    214         {
    215           SqlResult result = it.next();
    216           Float value = result.getFloat(valueIndex);
    217           short column = result.getShort(columnIndex);
    218           int position = posIndex > 0 ? result.getInt(posIndex) : 0;
    219           dataset.addValue((Number)value, position, columnToLabel.get(column));
    220         }
    221      
    222         // Create the plot and chart objects
    223           NumberAxis valueAxis = new NumberAxis(yLabel);
    224           CategoryAxis bioAssayAxis = new CategoryAxis();
    225           bioAssayAxis.setCategoryLabelPositions(CategoryLabelPositions.UP_90);
    226           bioAssayAxis.setVisible(showXLabels);
    227         Plot plot = new CategoryPlot(dataset, bioAssayAxis, valueAxis, new LineAndShapeRenderer());
    228         JFreeChart chart = new JFreeChart(plot);
     204
     205          String[] categoryAnnotations = null;
     206         
     207        JFreeChart chart = null;
     208        if ("box".equals(plotType))
     209        {
     210          // Collect all spot data values in one list per annotation group
     211          Map<AnnotationGroup, List<Float>> valuesPerGroup = new HashMap<AnnotationGroup, List<Float>>();
     212          AnnotationType at = AnnotationType.getById(dc, annotationTypeId);
     213          AnnotationSummary summary = explorer.getAnnotationSummary(dc, at);
     214          DynamicResultIterator it = query.iterate(dc);
     215          int valueIndex = it.getIndex("y");
     216          int columnIndex = it.getIndex(VirtualColumn.COLUMN.getName());
     217          int posIndex = positionIndex == ExperimentExplorer.SPOT_ALL ?
     218            it.getIndex(VirtualColumn.POSITION.getName()) : 0;
     219          while (it.hasNext())
     220          {
     221            SqlResult result = it.next();
     222            Float value = result.getFloat(valueIndex);
     223            if (value == null || value.isNaN()) continue;
     224            short column = result.getShort(columnIndex);
     225            AnnotationGroup grp = summary.getAnnotationGroup(column);
     226            List<Float> values = valuesPerGroup.get(grp);
     227            if (values == null)
     228            {
     229              values = new ArrayList<Float>();
     230              valuesPerGroup.put(grp, values);
     231            }
     232            values.add(value);
     233          }
     234         
     235          // Create the JFreeChart box-and-whisker dataset
     236          DefaultBoxAndWhiskerCategoryDataset dataset = new DefaultBoxAndWhiskerCategoryDataset();
     237          for (AnnotationGroup grp : summary.getAnnotationGroups())
     238          {
     239            List<Float> values = valuesPerGroup.get(grp);
     240            if (values == null || values.size() == 0) continue;
     241            Collections.sort(values);
     242            BoxAndWhiskerItem box = calculateBoxAndWhiskerStatistics(values);
     243            dataset.add(box, "", new ColumnKey(grp.hashCode(), grp.getTitle()));
     244          }
     245          categoryAxis.setLabel(at.getName());
     246          BoxAndWhiskerRenderer renderer = new BoxAndWhiskerRenderer();
     247          renderer.setMeanVisible(false);
     248          renderer.setMedianVisible(true);
     249          renderer.setFillBox(false);
     250          renderer.setAutoPopulateSeriesPaint(false);
     251          renderer.setBasePaint(Color.BLACK);
     252          renderer.setBaseOutlinePaint(Color.BLACK);
     253          Plot plot = new CategoryPlot(dataset, categoryAxis, valueAxis, renderer);
     254          chart = new JFreeChart(plot);
     255        }
     256        else if ("line".equals(plotType))
     257        {
     258          // Load annotation summaries
     259          Set<Integer> annotationTypes = explorer.getAnnotationTypeIds();
     260          List<AnnotationSummary> summaries = new ArrayList<AnnotationSummary>(3);
     261          if (showXLabels && annotationTypes != null && annotationTypes.size() > 0)
     262          {
     263            categoryAnnotations = new String[Math.min(3, annotationTypes.size())];
     264            int i = 0;
     265            for (Integer atId : annotationTypes)
     266            {
     267              AnnotationType at = AnnotationType.getById(dc, atId);
     268              summaries.add(explorer.getAnnotationSummary(dc, at));
     269              categoryAnnotations[i] = at.getName();
     270              ++i;
     271              if (summaries.size() == 3) break;
     272            }
     273          }
     274
     275          // Load bioassay information and related annotation group summaries
     276          Map<Short, ColumnKey> columnToLabel = new HashMap<Short, ColumnKey>();
     277          for (BioAssay ba : bioAssaySet.getBioAssays().list(dc))
     278          {
     279            short column = ba.getDataCubeColumnNo();
     280            ColumnKey key = new ColumnKey(ba.getId(), ba.getName());
     281            for (AnnotationSummary summary : summaries)
     282            {
     283              AnnotationGroup grp = summary.getAnnotationGroup(column);
     284              if (grp != null) key.setColor(summary.getAnnotationType().getName(), grp.getAwtColor());
     285            }
     286            columnToLabel.put(column, key);
     287          }
     288
     289          // Load the spot data into the dataset
     290          DefaultCategoryDataset dataset = new DefaultCategoryDataset();
     291          DynamicResultIterator it = query.iterate(dc);
     292          int valueIndex = it.getIndex("y");
     293          int columnIndex = it.getIndex(VirtualColumn.COLUMN.getName());
     294          int posIndex = positionIndex == ExperimentExplorer.SPOT_ALL ?
     295            it.getIndex(VirtualColumn.POSITION.getName()) : 0;
     296          while (it.hasNext())
     297          {
     298            SqlResult result = it.next();
     299            Float value = result.getFloat(valueIndex);
     300            if (value == null || value.isNaN()) continue;
     301            short column = result.getShort(columnIndex);
     302            int position = posIndex > 0 ? result.getInt(posIndex) : 0;
     303            dataset.addValue((Number)value, position, columnToLabel.get(column));
     304          }
     305       
     306          // Create the plot and chart objects
     307            categoryAxis.setCategoryLabelPositions(CategoryLabelPositions.UP_90);
     308            categoryAxis.setVisible(showXLabels);
     309          Plot plot = new CategoryPlot(dataset, categoryAxis, valueAxis, new LineAndShapeRenderer());
     310          chart = new JFreeChart(plot);
     311        }
    229312        chart.removeLegend();
    230313        if (title != null) chart.setTitle(title);
     
    235318        ChartRenderingInfo chartInfo = null;
    236319        int chartHeight = height;
    237         if (summaries.size() > 0)
     320        if (categoryAnnotations != null)
    238321        {
    239322          chartEntities = new StandardEntityCollection();
    240323          chartInfo = new ChartRenderingInfo(chartEntities);
    241           chartHeight -= 15 * summaries.size();
    242          
     324          chartHeight -= 15 * categoryAnnotations.length;
    243325        }
    244326        BufferedImage temp = chart.createBufferedImage(width, chartHeight, chartInfo);
    245         if (summaries.size() == 0)
    246         {
     327        if (categoryAnnotations == null)
     328        {
     329          // Use the image that JFreeChart generated if we don't have any annotations
    247330          image = temp;
    248331        }
    249332        else
    250333        {
     334          // Otherwise... create a new (bigger) image...
    251335          image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
    252336          Graphics2D g = image.createGraphics();
     
    254338          g.clearRect(0, 0, width, height);
    255339          g.setColor(Color.BLACK);
     340          // ... and copy the image from JFreeChart into it
    256341          g.drawImage(temp, 0, 0, width, chartHeight, 0, 0, width, chartHeight, null);
     342         
     343          // Draw annotation color rectangles
    257344          int minX = width;
    258           for (ChartEntity c : (Collection<ChartEntity>)chartEntities.getEntities())
    259           {
    260             if (c.getClass() == CategoryLabelEntity.class)
     345          for (ChartEntity chartEntity : (Collection<ChartEntity>)chartEntities.getEntities())
     346          {
     347            if (chartEntity.getClass() == CategoryLabelEntity.class)
    261348            {
    262               CategoryLabelEntity lbl = (CategoryLabelEntity)c;
     349              // This is the category (x) axis label object
     350              CategoryLabelEntity lbl = (CategoryLabelEntity)chartEntity;
     351              // Get the coordinates for the label
     352              Rectangle lblCoordinates = chartEntity.getArea().getBounds();
     353              if (lblCoordinates.getMinX() < minX) minX = (int)lblCoordinates.getMinX();
     354             
     355              ColumnKey key = (ColumnKey)lbl.getKey();
    263356              int currentY = chartHeight;
    264               for (AnnotationSummary summary : summaries)
     357              for (String annotation : categoryAnnotations)
    265358              {
    266                 AnnotationGroup grp = summary.getAnnotationGroup(labelToColumn.get(lbl.getKey()));
    267                 if (grp != null)
     359                Color color = key.getColor(annotation);
     360                if (color != null)
    268361                {
    269                   Rectangle r = c.getArea().getBounds();
    270                   if (r.getMinX() < minX) minX = (int)r.getMinX();
    271                   Rectangle r2 = new Rectangle((int)r.getMinX(), currentY, (int)r.getWidth(), 10);
    272                   g.setColor(grp.getAwtColor());
    273                   g.fill(r2);
     362                  // Draw colored rectangles below the label
     363                  Rectangle r = new Rectangle((int)lblCoordinates.getMinX(), currentY, (int)lblCoordinates.getWidth(), 10);
     364                  g.setColor(color);
     365                  g.fill(r);
    274366                  g.setColor(Color.LIGHT_GRAY);
    275                   g.draw(r2);
     367                  g.draw(r);
    276368                }
    277369                currentY += 15;
     
    281373          // Draw annotation titles
    282374          int currentY = chartHeight + 10;
    283           g.setPaint(bioAssayAxis.getLabelPaint());
     375          g.setPaint(categoryAxis.getLabelPaint());
    284376          g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
    285 
    286           Font lblFont = bioAssayAxis.getLabelFont();
     377          Font lblFont = categoryAxis.getLabelFont();
    287378          FontRenderContext context = g.getFontRenderContext();
    288           bioAssayAxis.getLabelInsets();
    289 
    290           for (AnnotationSummary summary : summaries)
    291           {
    292             String lbl = summary.getAnnotationType().getName();
    293             Rectangle2D bounds = lblFont.getStringBounds(lbl, context);
     379
     380          for (String annotation : categoryAnnotations)
     381          {
     382            // Try to calculate coordinate so that the text is right-aligned
     383            // near the first label
     384            Rectangle2D bounds = lblFont.getStringBounds(annotation, context);
    294385            int x = minX - (int)bounds.getWidth() - 5;
    295386            if (x < 0)
    296387            {
    297388              x = 0;
    298               lbl = StringUtil.trimString(lbl, (int)(lbl.length() * minX / bounds.getWidth()));
     389              annotation = StringUtil.trimString(annotation, (int)(annotation.length() * minX / bounds.getWidth()));
    299390            }
    300             g.drawString(lbl, x, currentY);
     391            g.drawString(annotation, x, currentY);
    301392            currentY += 15;
    302393          }
     
    386477  }
    387478 
     479  /**
     480    Creates a box-and-whisker data holder for the given list of values.
     481    The data holder will be populated with the median and the 5th, 25th, 75th and
     482    95th percentile values as follows:
     483    <ul>
     484    <li>median = BAWI.getMedian()
     485    <li>5th percentile = BAWI.getMinRegularValue()
     486    <li>25th percentile = BAWI.getQ1()
     487    <li>75th percentile = BAWI.getQ3()
     488    <li>95th percentile = BAWI.getMaxRegularValue()
     489    </ul>
     490    The mean and outlier values are currently not calculated (may change in
     491    the future).
     492   
     493    @param values The list of values which must be sorted in ascending order
     494    @return A BoxAndWhiskerItem object
     495  */
     496  public BoxAndWhiskerItem calculateBoxAndWhiskerStatistics(List<Float> values)
     497  {
     498    float median = getPercentile(values, 50);
     499    float p5 = getPercentile(values, 5);
     500    float p25 = getPercentile(values, 25);
     501    float p75 = getPercentile(values, 75);
     502    float p95 = getPercentile(values, 95);
     503    return new BoxAndWhiskerItem(Float.NaN, median, p25, p75, p5, p95, Float.NaN, Float.NaN, null);
     504  }
     505 
     506  /**
     507    Calculates the percentile values from a sorted list of values.
     508    If the percentile falls between two elements in the list the
     509    average of the two nearest elements are used.
     510   
     511    @param values The values which must be sorted
     512    @param percentile The percentile, a value between 0 and 100
     513    @return The percentile value, or Float.NaN if it could not be
     514      calculated
     515  */
     516  public float getPercentile(List<? extends Number> values, int percentile)
     517  {
     518    int size = values.size();
     519    if (size == 0) return Float.NaN;
     520    if (size == 1) return values.get(0).floatValue();
     521   
     522    int width = size + 1;
     523    int pos = width * percentile / 100;
     524    if (pos == 0)
     525    {
     526       // Overflow to the left -- return first value
     527      return values.get(0).floatValue();
     528    }
     529    else if (pos >= size)
     530    {
     531       // Overflow to the right -- return last value
     532      return values.get(size-1).floatValue();
     533    }
     534   
     535    if (width * percentile % 100 == 0)
     536    {
     537      // Exact hit -- return one value
     538      return values.get(pos-1).floatValue();
     539    }
     540    else
     541    {
     542      // Hit between two values -- return the average
     543      return (values.get(pos-1).floatValue() + values.get(pos).floatValue())/2;
     544    }
     545  }
     546 
     547  /**
     548    Uses as a column key in the plots. This allows us to
     549    separate the displayed label from the identity of the column.
     550    Eg. there is no need to make sure that the label strings are unique
     551    since we can use some internal id for this purpose.
     552    <p>
     553    Additionally, this class allows us to map annotations to colors
     554    that are used to draw small colored boxes below each column label.
     555  */
     556  public static class ColumnKey
     557    implements Comparable<ColumnKey>
     558  {
     559    private final Comparable id;
     560    private final String title;
     561    private final Map<String, Color> annotations;
     562   
     563    public ColumnKey(Comparable id, String title)
     564    {
     565      this.id = id;
     566      this.title = title;
     567      this.annotations = new HashMap<String, Color>();
     568    }
     569
     570    /*
     571      From the Comparable interface
     572      -----------------------------
     573    */
     574    /**
     575      The ID of the key determines equality.
     576    */
     577    @SuppressWarnings("unchecked")
     578    @Override
     579    public int compareTo(ColumnKey o)
     580    {
     581      return id.compareTo(o.id);
     582    }
     583    // -------------------------------
     584   
     585    /*
     586      From the Object class
     587      -------------------------------
     588    */
     589    @Override
     590    public String toString()
     591    {
     592      return title;
     593    }
     594   
     595    @Override
     596    public boolean equals(Object o)
     597    {
     598      if (o == null) return false;
     599      if (this == o) return true;
     600      if (o.getClass() != getClass()) return false;
     601      ColumnKey ck = (ColumnKey)o;
     602      return id.equals(ck.id);
     603    }
     604   
     605    @Override
     606    public int hashCode()
     607    {
     608      return id.hashCode();
     609    }
     610    // ------------------------------------
     611   
     612    public void setColor(String annotation, Color color)
     613    {
     614      annotations.put(annotation, color);
     615    }
     616   
     617    public Color getColor(String annotation)
     618    {
     619      return annotations.get(annotation);
     620    }
     621   
     622  }
     623 
    388624}
  • trunk/www/views/experiments/explorer/view/plotter.jsp

    r5114 r5138  
    7474  final int reporterIndex = Values.getInt(request.getParameter("reporterIndex"));
    7575  final int positionIndex = Values.getInt(request.getParameter("positionIndex"));
     76  final String plotType = Values.getString(request.getParameter("type"), "line");
     77  final int annotationTypeId = Values.getInt(request.getParameter("annotationTypeId"));
    7678  final boolean needAverageMethod = positionIndex == ExperimentExplorer.SPOT_AVG;
    7779 
    78   BioAssaySet bas = BioAssaySet.getById(dc, bioAssaySetId);
    79   RawDataType rdt = bas.getRawDataType();
    80   Experiment experiment = bas.getExperiment();
    81   int maxRawMappings = bas.getMaxRawMappingsForSpot();
    82   IntensityTransform transform = bas.getIntensityTransform();
     80  final BioAssaySet bas = BioAssaySet.getById(dc, bioAssaySetId);
     81  final RawDataType rdt = bas.getRawDataType();
     82  final Experiment experiment = bas.getExperiment();
     83  final int maxRawMappings = bas.getMaxRawMappingsForSpot();
     84  final IntensityTransform transform = bas.getIntensityTransform();
     85  final ExperimentExplorer explorer = ExperimentExplorer.getExplorer(bas);
     86  final List<AnnotationType> annotationTypes = explorer.getAnnotationTypes(dc, true);
    8387 
    8488  List<TableColumn> formulas = new LinkedList<TableColumn>();
     
    131135  {
    132136    var plotType = getPlotType();
    133     if (plotType == 'scatter')
    134     {
    135       return validateScatterPlot();
     137    if (plotType == 'line')
     138    {
     139      return validateLinePlot();
     140    }
     141    else if (plotType == 'box')
     142    {
     143      return validateBoxPlot();
    136144    }
    137145    return false;
    138146  }
    139   function validateScatterPlot()
    140   {
    141     var frm = document.forms['scatter'];
     147 
     148  function validateLinePlot()
     149  {
     150    var frm = document.forms['line'];
    142151    if (Main.trimString(frm.yFormula.value) == '')
    143152    {
     
    149158  }
    150159 
    151   var plotType = 'scatter';
     160  function validateBoxPlot()
     161  {
     162    var frm = document.forms['box'];
     163    if (Main.trimString(frm.yFormula.value) == '')
     164    {
     165      alert("You must enter an expression for the Y axis");
     166      frm.yFormula.focus();
     167      return false;
     168    }
     169    return true;
     170  }
     171 
     172  var plotType = '<%=plotType%>';
    152173  function getPlotType()
    153174  {
     
    157178  function switchTab(tabControlId, tabId)
    158179  {
    159     if (tabId == 'scatter' || tabId == 'histogram')
     180    if (tabId == 'line' || tabId == 'box')
    160181    {
    161182      plotType = tabId;
     
    167188  {
    168189    var index = list.selectedIndex;
    169     var frm = document.forms['scatter'];
     190    var frm = list.form;
    170191    if (frm.averageMethod)
    171192    {
     
    193214        url += '&height='+plotFrm.height.value;
    194215      }
    195  
    196216      var plotType = getPlotType();
    197       if (plotType == 'scatter')
    198       {
    199         var frm = document.forms['scatter'];
    200         url += '&type=scatter';
     217      if (plotType == 'line')
     218      {
     219        var frm = document.forms['line'];
     220        url += '&type=line';
    201221        url += '&y='+Main.encodeURI(frm.yFormula.value);
    202222        url += '&yLog='+(frm.yLog.checked ? 1 : 0);
     
    207227          url += '&averageMethod=' + frm.averageMethod[frm.averageMethod.selectedIndex].value;
    208228        }
     229      }
     230      else if (plotType == 'box')
     231      {
     232        var frm = document.forms['box'];
     233        url += '&type=box';
     234        url += '&y='+Main.encodeURI(frm.yFormula.value);
     235        url += '&yLog='+(frm.yLog.checked ? 1 : 0);
     236        url += '&yLabel='+Main.encodeURI(frm.yLabel.value);
     237        url += '&annotationTypeId=' + frm.annotationTypeId[frm.annotationTypeId.selectedIndex].value;
    209238      }
    210239      url += '&' + new Date().getTime();
     
    326355      style="<%="width: "+(int)(scale*340)+"px;"%>"
    327356      contentstyle="<%="height: "+(int)(scale*340)+"px;"%>"
     357      active="<%=plotType%>" remember="false"
    328358      switch="switchTab">
    329     <t:tab id="scatter" title="Scatter plot" helpid="plotter.scatterplot"
    330       tooltip="Create a scatter plot">
    331       <form name="scatter">
     359    <t:tab id="line" title="Line plot" helpid="explorer.lineplot"
     360      tooltip="Create a line plot with bioassays along the x axis">
     361      <form name="line">
    332362      <table border="0" cellspacing="0" cellpadding="2" class="form">
    333363      <tr>
     
    353383            image="expression_builder.gif"
    354384            tooltip="Use the Expression builder"
    355             onclick="openExpressionBuilder('Y-axis expression', 'scatter', 'yFormula', 'COLUMN_EXPRESSION')"
     385            onclick="openExpressionBuilder('Y-axis expression', 'line', 'yFormula', 'COLUMN_EXPRESSION')"
    356386          />
    357387        </td>
     
    398428      </table>
    399429      </form>
    400     </t:tab>   
     430    </t:tab>
     431    <t:tab id="box" title="Box plot" helpid="explorer.boxplot"
     432      tooltip="Create a box plot with annotation values along the x axis">
     433      <form name="box">
     434      <table border="0" cellspacing="0" cellpadding="2" class="form">
     435      <tr>
     436        <td class="prompt" colspan="3">Y-axis</td>
     437      </tr>
     438      <tr>
     439        <td>&nbsp;Presets</td>
     440        <td colspan="2">
     441        <select name="yPresets" style="width: 20em;"
     442          onchange="presetOnChange(this, this.form.yFormula, this.form.yLabel)"
     443          >
     444          <option value="">- select from list or enter formula below -
     445          <%=formulaOptions.toString()%>
     446        </select>
     447        </td>
     448      </tr>
     449      <tr>
     450        <td>&nbsp;Expression</td>
     451        <td><input type="text" class="text required" size="30" maxlength="255" name="yFormula"></td>
     452        <td>
     453          <base:button
     454            title=""
     455            image="expression_builder.gif"
     456            tooltip="Use the Expression builder"
     457            onclick="openExpressionBuilder('Y-axis expression', 'box', 'yFormula', 'COLUMN_EXPRESSION')"
     458          />
     459        </td>
     460      </tr>
     461      <tr>
     462        <td>&nbsp;Label</td>
     463        <td colspan="2"><input type="text" class="text" size="30" maxlength="255" name="yLabel"></td>
     464      </tr>
     465      <tr>
     466        <td>&nbsp;Log scale</td>
     467        <td colspan="2"><input type="checkbox" name="yLog" value="1"></td>
     468      </tr>
     469      <%
     470      if (positionIndex == ExperimentExplorer.SPOT_AVG)
     471      {
     472        %>
     473        <tr>
     474          <td>&nbsp;Average</td>
     475          <td>
     476            <select name="averageMethod">
     477            <%
     478            for (Formula.AverageMethod method : Formula.AverageMethod.values())
     479            {
     480              if (method != Formula.AverageMethod.NONE)
     481              {
     482                %>
     483                <option value="<%=method.name()%>"><%=method.toString()%></option>
     484                <%
     485              }
     486            }
     487            %>
     488            </select>
     489          </td>
     490        <% 
     491      }
     492      %>
     493      <tr>
     494        <td class="prompt" colspan="3">X-axis</td>
     495      </tr>
     496      <tr>
     497        <td>&nbsp;Annotation</td>
     498        <td>
     499          <select name="annotationTypeId">
     500          <%
     501          for (AnnotationType at : annotationTypes)
     502          {
     503            String selected = at.getId() == annotationTypeId ? "selected" : "";
     504            %>
     505            <option value="<%=at.getId()%>" <%=selected%>><%=HTML.encodeTags(at.getName())%>
     506            <%
     507          }
     508          %>
     509          </select>
     510        </td>
     511      </tr>
     512      </table>
     513      </form>
     514    </t:tab>
    401515    </t:tabcontrol>
    402516    </td>
  • trunk/www/views/experiments/explorer/view/view.jsp

    r5137 r5138  
    256256    function plotSpotData()
    257257    {
    258       var url = 'plotter.jsp?ID=<%=ID%>';
     258      var url = 'plotter.jsp?ID=<%=ID%>&type=line';
    259259      url += '&bioAssaySetId=<%=bioAssaySetId%>';
    260260      url += '&reporterIndex=<%=reporterIndex%>';
    261261      url += '&positionIndex=<%=positionIndex%>';
    262262      Main.openPopup(url, 'SpotPlot', 1100, 700);
     263    }
     264    function boxPlot(annotationType)
     265    {
     266      var url = 'plotter.jsp?ID=<%=ID%>&type=box';
     267      url += '&bioAssaySetId=<%=bioAssaySetId%>';
     268      url += '&reporterIndex=<%=reporterIndex%>';
     269      url += '&positionIndex=<%=positionIndex%>';
     270      url += '&annotationTypeId=' + annotationType;
     271      Main.openPopup(url, 'BoxPlot', 1100, 700);
    263272    }
    264273  </script>
     
    458467            <tr>
    459468              <td class="summaryheader"><%=Base.getLinkedName(ID, at, false, true)%></td>
     469              <td class="summaryheader"><base:icon
     470                image="plotter.gif"
     471                onclick="<%="boxPlot(" + at.getId() + ")"%>"
     472                tooltip="Box plot for selected spot data per annotation group"
     473              /></td>
    460474              <%
    461475              for (AnnotationGroup ag : summary.getAnnotationGroups())
     
    474488                %>
    475489                <tr>
    476                 <td>Mean ch <%=ch%> int.</td>
     490                <td colspan="2">Mean ch <%=ch%> int.</td>
    477491                <%
    478492                for (AnnotationGroup ag : summary.getAnnotationGroups())
     
    490504                %>
    491505                <tr>
    492                 <td title="The geometric mean of the ratios">G. mean ratio</td>
     506                <td colspan="2" title="The geometric mean of the ratios">G. mean ratio</td>
    493507                <%
    494508                for (AnnotationGroup ag : summary.getAnnotationGroups())
     
    501515                </tr>
    502516                <tr>
    503                 <td title="Standard deviation of log2 ratios">log2ratio SD</td>
     517                <td colspan="2" title="Standard deviation of log2 ratios">log2ratio SD</td>
    504518                <%
    505519                for (AnnotationGroup ag : summary.getAnnotationGroups())
     
    512526                </tr>
    513527                <tr>
    514                 <td title="The number of spots falling in this group">Count</td>
     528                <td colspan="2" title="The number of spots falling in this group">Count</td>
    515529                <%
    516530                for (AnnotationGroup ag : summary.getAnnotationGroups())
Note: See TracChangeset for help on using the changeset viewer.