Home | History | Annotate | Download | only in ahat
      1 /*
      2  * Copyright (C) 2015 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.android.ahat;
     18 
     19 import java.net.URI;
     20 import java.net.URISyntaxException;
     21 
     22 /**
     23  * A class representing a small string of document content consisting of text,
     24  * links, images, etc.
     25  */
     26 class DocString {
     27   private StringBuilder mStringBuilder;
     28 
     29   public DocString() {
     30     mStringBuilder = new StringBuilder();
     31   }
     32 
     33   /**
     34    * Construct a new DocString, initialized with the given text.
     35    */
     36   public static DocString text(String str) {
     37     DocString doc = new DocString();
     38     return doc.append(str);
     39   }
     40 
     41   /**
     42    * Construct a new DocString, initialized with the given formatted text.
     43    */
     44   public static DocString format(String format, Object... args) {
     45     DocString doc = new DocString();
     46     return doc.appendFormat(format, args);
     47   }
     48 
     49   /**
     50    * Construct a new DocString, initialized with the given link.
     51    */
     52   public static DocString link(URI uri, DocString content) {
     53     DocString doc = new DocString();
     54     return doc.appendLink(uri, content);
     55   }
     56 
     57   /**
     58    * Construct a new DocString initialized with the given image.
     59    */
     60   public static DocString image(URI uri, String alt) {
     61     return (new DocString()).appendImage(uri, alt);
     62   }
     63 
     64   /**
     65    * Append literal text to the given doc string.
     66    * Returns this object.
     67    */
     68   public DocString append(String text) {
     69     mStringBuilder.append(HtmlEscaper.escape(text));
     70     return this;
     71   }
     72 
     73   /**
     74    * Append formatted text to the given doc string.
     75    * Returns this object.
     76    */
     77   public DocString appendFormat(String format, Object... args) {
     78     append(String.format(format, args));
     79     return this;
     80   }
     81 
     82   public DocString append(DocString str) {
     83     mStringBuilder.append(str.html());
     84     return this;
     85   }
     86 
     87   /**
     88    * Adorn the given string to indicate it represents something added relative
     89    * to a baseline.
     90    */
     91   public static DocString added(DocString str) {
     92     DocString string = new DocString();
     93     string.mStringBuilder.append("<span class=\"added\">");
     94     string.mStringBuilder.append(str.html());
     95     string.mStringBuilder.append("</span>");
     96     return string;
     97   }
     98 
     99   /**
    100    * Adorn the given string to indicate it represents something added relative
    101    * to a baseline.
    102    */
    103   public static DocString added(String str) {
    104     return added(text(str));
    105   }
    106 
    107   /**
    108    * Adorn the given string to indicate it represents something removed relative
    109    * to a baseline.
    110    */
    111   public static DocString removed(DocString str) {
    112     DocString string = new DocString();
    113     string.mStringBuilder.append("<span class=\"removed\">");
    114     string.mStringBuilder.append(str.html());
    115     string.mStringBuilder.append("</span>");
    116     return string;
    117   }
    118 
    119   /**
    120    * Adorn the given string to indicate it represents something removed relative
    121    * to a baseline.
    122    */
    123   public static DocString removed(String str) {
    124     return removed(text(str));
    125   }
    126 
    127   /**
    128    * Standard formatted DocString for describing a size.
    129    *
    130    * Nothing is printed for a size of zero.
    131    * Set isPlaceHolder to true to indicate that the size field corresponds to
    132    * for a place holder object that should be annotated specially.
    133    */
    134   public static DocString size(long size, boolean isPlaceHolder) {
    135     DocString string = new DocString();
    136     if (isPlaceHolder) {
    137       string.append(DocString.removed("del"));
    138     } else if (size != 0) {
    139       string.appendFormat("%,14d", size);
    140     }
    141     return string;
    142   }
    143 
    144   /**
    145    * Standard formatted DocString for describing a change in size relative to
    146    * a baseline.
    147    * @param noCurrent - whether no current object exists.
    148    * @param noBaseline - whether no basline object exists.
    149    * @param current - the size of the current object.
    150    * @param baseline - the size of the baseline object.
    151    */
    152   public static DocString delta(boolean noCurrent, boolean noBaseline,
    153       long current, long baseline) {
    154     DocString doc = new DocString();
    155     return doc.appendDelta(noCurrent, noBaseline, current, baseline);
    156   }
    157 
    158   /**
    159    * Standard formatted DocString for describing a change in size relative to
    160    * a baseline.
    161    */
    162   public DocString appendDelta(boolean noCurrent, boolean noBaseline,
    163       long current, long baseline) {
    164     if (noCurrent) {
    165       append(removed(format("%+,14d", 0 - baseline)));
    166     } else if (noBaseline) {
    167       append(added("new"));
    168     } else if (current > baseline) {
    169       append(added(format("%+,14d", current - baseline)));
    170     } else if (current < baseline) {
    171       append(removed(format("%+,14d", current - baseline)));
    172     }
    173     return this;
    174   }
    175 
    176   public DocString appendLink(URI uri, DocString content) {
    177     mStringBuilder.append("<a href=\"");
    178     mStringBuilder.append(uri.toASCIIString());
    179     mStringBuilder.append("\">");
    180     mStringBuilder.append(content.html());
    181     mStringBuilder.append("</a>");
    182     return this;
    183   }
    184 
    185   public DocString appendImage(URI uri, String alt) {
    186     mStringBuilder.append("<img alt=\"");
    187     mStringBuilder.append(HtmlEscaper.escape(alt));
    188     mStringBuilder.append("\" src=\"");
    189     mStringBuilder.append(uri.toASCIIString());
    190     mStringBuilder.append("\" />");
    191     return this;
    192   }
    193 
    194   public DocString appendThumbnail(URI uri, String alt) {
    195     mStringBuilder.append("<img height=\"16\" alt=\"");
    196     mStringBuilder.append(HtmlEscaper.escape(alt));
    197     mStringBuilder.append("\" src=\"");
    198     mStringBuilder.append(uri.toASCIIString());
    199     mStringBuilder.append("\" />");
    200     return this;
    201   }
    202 
    203   /**
    204    * Convenience function for constructing a URI from a string with a uri
    205    * known to be valid.
    206    */
    207   public static URI uri(String uriString) {
    208     try {
    209       return new URI(uriString);
    210     } catch (URISyntaxException e) {
    211       throw new IllegalStateException("Known good uri has syntax error: " + uriString, e);
    212     }
    213   }
    214 
    215   /**
    216    * Convenience function for constructing a URI from a formatted string with
    217    * a uri known to be valid.
    218    */
    219   public static URI formattedUri(String format, Object... args) {
    220     return uri(String.format(format, args));
    221   }
    222 
    223   /**
    224    * Render the DocString as html.
    225    */
    226   public String html() {
    227     return mStringBuilder.toString();
    228   }
    229 }
    230