Interactive Plot Widget

In [1]:
def plot = new Plot(title: "Setting line properties")
def ys = [0, 1, 6, 5, 2, 8]
def ys2 = [0, 2, 7, 6, 3, 8]
plot << new Line(y: ys, width: 10, color: Color.red)
plot << new Line(y: ys, width: 3, color: Color.yellow)
plot << new Line(y: ys, width: 4, color: new Color(33, 87, 141), style: StrokeType.DASH, interpolation: 0)
plot << new Line(y: ys2, width: 2, color: new Color(212, 57, 59), style: StrokeType.DOT)
plot << new Line(y: [5, 0], x: [0, 5], style: StrokeType.LONGDASH)
plot << new Line(y: [4, 0], x: [0, 5], style: StrokeType.DASHDOT)
Out[1]:

In [2]:
new Plot().add(new Line(x: [0, 1, 2, 3, 4, 5], y: [0, 1, 6, 5, 2, 8]))
new Plot().add(new Line(x: (0..5), y: [0, 1, 6, 5, 2, 8]))
new Plot() << new Line(x: (0..5), y: [0, 1, 6, 5, 2, 8])
Out[2]:

In [3]:
def plot = new Plot();
def y1 = [1.5, 1, 6, 5, 2, 8]
def cs = [Color.black, Color.red, Color.gray, Color.green, Color.blue, Color.pink]
def ss = [StrokeType.SOLID, StrokeType.SOLID, StrokeType.DASH, StrokeType.DOT, StrokeType.DASHDOT, StrokeType.LONGDASH]
plot << new Stems(y: y1, color: cs, style: ss, width: 5)
Out[3]:

In [4]:
def plot = new Plot(title: "Bars")
def cs = [new Color(255, 0, 0, 128)] * 5 // transparent bars
cs[3] = Color.red // set color of a single bar, solid colored bar
plot << new Bars(x: (1..5), y: [3, 5, 2, 3, 7], color: cs, outlineColor: Color.black, width: 0.3)
Out[4]:

In [5]:
def plot = new Plot(title: "Changing Point Size, Color, Shape")
def y1 = [6, 7, 12, 11, 8, 14]
def y2 = y1.collect { it - 2 }
def y3 = y2.collect { it - 2 }
def y4 = y3.collect { it - 2 }
plot << new Points(y: y1)
plot << new Points(y: y2, shape: ShapeType.CIRCLE)
plot << new Points(y: y3, size: 8.0, shape: ShapeType.DIAMOND)
plot << new Points(y: y4, size: 12.0, color: Color.orange, outlineColor: Color.red)
Out[5]:

In [6]:
def plot = new Plot(title: "Changing point properties with list")
def cs = [Color.black, Color.red, Color.orange, Color.green, Color.blue, Color.pink]
def ss = [6.0, 9.0, 12.0, 15.0, 18.0, 21.0]
def fs = [false, false, false, true, false, false]
plot << [new Points(y: [5] * 6, size: 12.0, color: cs),
         new Points(y: [4] * 6, size: 12.0, color: Color.gray, outlineColor: cs),
         new Points(y: [3] * 6, size: ss, color: Color.red),
         new Points(y: [2] * 6, size: 12.0, color: Color.black, fill: fs, outlineColor: Color.black)]
Out[6]:

In [7]:
def plot = new Plot()
def y = [3, 5, 2, 3]
def x0 = [0, 1, 2, 3]
def x1 = [3, 4, 5, 8]
plot << new Area(x: x0, y: y)
plot << new Area(x: x1, y: y, color: new Color(128, 128, 128, 50), interpolation: 0)
Out[7]:

In [8]:
def p = new Plot()
p << new Line(y: [3, 6, 12, 24], displayName: "Median")
p << new Area(y: [4, 8, 16, 32], base: [2, 4, 8, 16],
              color: new Color(255, 0, 0, 50), displayName: "Q1 to Q3")
Out[8]:

In [9]:
def y1 = [1,5,3,2,3]
def y2 = [7,2,4,1,3]
def p = new Plot(title: 'Plot with XYStacker', initHeight: 200)
def a1 = new Area(y: y1, displayName: 'y1')
def a2 = new Area(y: y2, displayName: 'y2')
p << XYStacker.stack([a1, a2])
Out[9]:

In [10]:
def p = new Plot ()
p << new Line(y: [-1, 1])
p << new ConstantLine(x: 0.65, style: StrokeType.DOT, color: Color.blue)
p << new ConstantLine(y: 1, style: StrokeType.DASHDOT, color: Color.blue)
p << new ConstantLine(x: 1, y: 0.4, color: Color.gray, width: 5, showLabel: true)
Out[10]:

In [11]:
new Plot() << new Line(y: [-3, 1, 3, 4, 5]) << new ConstantBand(x: [1, 2], y: [1, 3])
Out[11]:

In [12]:
def p = new Plot() 
p << new Line(x: [-3, 1, 2, 4, 5], y: [4, 2, 6, 1, 5])
p << new ConstantBand(x: [Double.NEGATIVE_INFINITY, 1], color: new Color(128, 128, 128, 50))
p << new ConstantBand(x: [1, 2])
p << new ConstantBand(x: [4, Double.POSITIVE_INFINITY])
Out[12]:

In [13]:
def plot = new Plot()
def xs = (1..10)
def ys = [8.6, 6.1, 7.4, 2.5, 0.4, 0.0, 0.5, 1.7, 8.4, 1]
def label = { i ->
  if (ys[i] > ys[i+1] && ys[i] > ys[i-1]) return "max"
  if (ys[i] < ys[i+1] && ys[i] < ys[i-1]) return "min"
  if (ys[i] > ys[i-1]) return "rising"
  if (ys[i] < ys[i-1]) return "falling"
  return ""
}
for (i = 0; i < xs.size(); i++) {
  if (i > 0 && i < xs.size()-1)
    plot << new Text(x: xs[i], y: ys[i], text: label(i),  pointerAngle: -i/3.0)
}
plot << new Line(x: xs, y: ys)
plot << new Points(x: xs, y: ys)
Out[13]:

In [3]:
def ch = new Crosshair(color: new Color(255, 128, 5), width: 2, style: StrokeType.DOT)
pp = new Plot(crosshair: ch, omitCheckboxes: true,
                  legendLayout: LegendLayout.HORIZONTAL, legendPosition: LegendPosition.TOP)
def x = [1, 4, 6, 8, 10]
def y = [3, 6, 4, 5, 9]
pp << new Line(displayName: "Line", x: x, y: y, width: 3)
pp << new Bars(displayName: "Bar", x: (1..10), y: [2, 2, 4, 4, 2, 2, 0, 2, 2, 4], width: 0.5)
pp << new Points(x: x, y: y, size: 10, toolTip: {xs, ys -> "x = " + xs + ", y = " + ys })
In [5]:
pp.setLegendPosition(LegendPosition.TOP);
"ok"
Out[5]:
ok
In [15]:
import com.twosigma.beaker.fileloader.CsvPlotReader

def rates = new CsvPlotReader().readAsList("tableRows.csv")

new SimpleTimePlot(rates, ["y1", "y10"],
                   yLabel: "Price", 
                   displayNames: ["1 Year", "10 Year"])
Out[15]:

In [16]:
def points = 100;
def logBase = 10;
def expys = [];
def xs = [];
for(int i = 0; i < points; i++){
  xs[i] = i / 15.0;
  expys[i] = Math.exp(xs[i]); 
}

def cplot = new CombinedPlot(xLabel: "Linear");
def logYPlot = new Plot(title: "Linear x, Log y", yLabel: "Log", logY: true, yLogBase: logBase);
logYPlot << new Line(x: xs, y: expys, displayName: "f(x) = exp(x)");
logYPlot << new Line(x: xs, y: xs, displayName: "g(x) = x");
cplot.add(logYPlot, 3);

// works for 2nd Y axis too:
// logYPlot << new YAxis(label: "Right Log Y-Axis", log: true, logBase: logBase);

def linearYPlot = new Plot(title: "Linear x, Linear y", yLabel: "Linear");
linearYPlot << new Line(x: xs, y: expys, displayName: "f(x) = exp(x)");
linearYPlot << new Line(x: xs, y: xs, displayName: "g(x) = x");
cplot.add(linearYPlot, 3);

cplot
Out[16]:

In [17]:
def points = 100;
def logBase = 10;
def expys = [];
def xs = [];
for(int i = 0; i < points; i++){
  xs[i] = i /15
  expys[i] = Math.exp(xs[i]);
}

def plot = new Plot(title: "Log x, Log y", xLabel: "Log", yLabel: "Log",
                    logX: true, xLogBase: logBase, logY: true, yLogBase: logBase);

plot << new Line(x: xs, y: expys, displayName: "f(x) = exp(x)");
plot << new Line(x: xs, y: xs, displayName: "f(x) = x");

plot
Out[17]:

In [18]:
def cal = Calendar.getInstance();
cal.add(Calendar.HOUR, -1)

def today = new Date();
def millis = today.time;
def hour = 1000 * 60 * 60;

def plot = new TimePlot(
  timeZone: new SimpleTimeZone(10800000, "America/New_York")
);
//list of milliseconds
plot << new Points(x:(0..10).collect{millis + hour * it}, y:(0..10), size: 10, displayName: "milliseconds");
//list of java.util.Date objects
plot << new Points(x:(0..10).collect{cal.add(Calendar.HOUR, 1); cal.getTime()}, y:(0..10), size: 4, displayName: "date objects");
Out[18]:

In [19]:
def today  = new Date()
def millis = today.time
def nanos  = millis * 1000 * 1000g // g makes it arbitrary precision
def np = new NanoPlot()
np << new Points(x:(0..10).collect{nanos + 7 * it}, y:(0..10))
Out[19]:

In [20]:
import com.twosigma.beaker.chart.xychart.*
import com.twosigma.beaker.chart.legend.*
import com.twosigma.beaker.chart.xychart.plotitem.*
import com.twosigma.beaker.chart.Color

r = new Random()
p = new Plot(title: "Advanced Plot Styling",
         labelStyle: "font-size:32px; font-weight: bold; font-family: courier; fill: green;",
         gridLineStyle:  "stroke: purple; stroke-width: 3;",
         titleStyle: "color: green;"
        )
p << new Points(x: (1..1000).collect { r.nextGaussian() * 10.0d },
                y: (1..1000).collect { r.nextGaussian() * 20.0d })
Out[20]:

In [21]:
import java.nio.file.Files
byte[] picture = Files.readAllBytes(new File("widgetArch.png").toPath());
def p =  new Plot();
// x y width height are coordinates, opacity is a double in 0~1

// image can be loaded via bytes, filepath, or url
p << new Rasters(x: [-10,3], y: [3,1.5], width: [6,5], height:[10,8], opacity: [1,0.5], dataString: picture);
//p << new Rasters(x: -1, y: 4.5, width: 5, height: 8, opacity:0.5, filePath: "widgetArch.png");
p << new Rasters(x: [-4], y: [10.5], width: [7], height: [2], opacity:[1], fileUrl: "https://www.twosigma.com/static/img/twosigma.png");

// a list of images!
def x = [-8, -5, -3, -2, -1, 1, 2, 4, 6, 8]
def y = [4, 5, 1, 2, 0 ,3, 6, 4, 5, 9]
def width = [1, 1, 1, 1, 1, 1, 1, 1, 1, 1]
def opacity = [0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1]
p << new Rasters(x: x, y: y, width:width, height:width, opacity:opacity,fileUrl: "http://icons.iconarchive.com/icons/paomedia/small-n-flat/1024/sign-check-icon.png")
Out[21]:

In [22]:
def plot = new Plot(title: "Setting 2nd Axis bounds")
def ys = [0, 2, 4, 6, 15, 10]
def ys2 = [-40, 50, 6, 4, 2, 0]
def ys3 = [3, 6, 3, 6, 70, 6]
plot << new YAxis(label:"Spread")
plot << new Line(y: ys)
plot << new Line(y: ys2, yAxis: "Spread")
plot.getYAxes()[0].setBound(1,5);
plot.getYAxes()[1].setBound(3,6) // this should change the bounds of the 2nd, right axis
plot
Out[22]:

In [1]:
new Line(y: [4, 0], x: [0, 5])