Mercurial > lbo > hg > myi3stat
changeset 15:7432c90d5c07
Add details on how to add a new metric
author | Lewin Bormann <lbo@spheniscida.de> |
---|---|
date | Sun, 14 Feb 2016 15:15:09 +0100 |
parents | 61cdb00a3a84 |
children | d40c9e075232 |
files | README.md |
diffstat | 1 files changed, 82 insertions(+), 0 deletions(-) [+] |
line wrap: on
line diff
--- a/README.md Sun Feb 14 14:56:04 2016 +0100 +++ b/README.md Sun Feb 14 15:15:09 2016 +0100 @@ -4,3 +4,85 @@ easily extend your i3 status bar. It is configured mainly via command line arguments, and can be extended by small custom metrics. +## How to add your metric + +### Define a metric type + +Create a new module under `src/metrics/`, and define your type: + + struct MyCustomMetric; + +You usually don't need any data members, as state between runs is carried in a +framework-supplied `MetricState` container. + +### Implement the `Metric` trait + +Implement the `Metric` trait for your type. + + pub trait Metric { + fn init(&self, st: &mut MetricState, initarg: Option<String>); + fn render(&self, st: &mut MetricState) -> RenderResult; + } + +The `init()` method takes a `MetricState` object, and an optional argument. The +argument is a user-supplied string from the command line invocation (see below, +"Register your metric"). `MetricState` is a quite simple type: + + // use framework::*; + // Essentially a map of arbitrary keys to dynamically-typed State entries (see below). + impl MetricState { + pub fn get(&self, k: String) -> State; + pub fn set(&mut self, k: String, v: State); + // Obtain current timestamp. + pub fn now() -> i64; + // Time (Unix epoch) of last call. + pub last_called: i64; + } + pub enum State { + Empty, + S(String), + I(i64), + F(f64), + C(Color), + } + +Every time your metric is asked to `render()`, it is given the same +`MetricState` object; `last_called` is set to the timestamp of the previous +invocation (so you can compute a rate, for example); it has second-resolution. +You can arbitrarily get and set values on the `MetricState`. + +Typically you will set some constant configuration parameters at the invocation +of your `init()` method, and use them later to determine how exactly you'll +render the metric. + +At the end of your `render()` implementation, you return a `RenderResult`: + + RenderResult::new(contents, Color::Red) + +This is the actual output that will appear. + +Finally, export a factory function that creates an instance of your metric: + + pub fn make_your_metric() -> Box<Metric> { Box::new(MyCustomMetric) } + +### Register your new metric + +In `src/main.rs`, you need to register your metric inside the +`register_metrics()` function near the end of the file: + + use metric::your_metric; + registry.register_metric("your_metric", + "A metric that shows how frobnicated your foos are", // Short description + "format string", // config parameter description + your_metric::make_your_metric()); // An instance of your metric, of type Box<Metric> + +This will add a command line flag that can be specified by users to activate +your metric, i.e., make it show up. There will also be a snippet of +documentation that is displayed when the user calls for `--help`: + + --your_metric [format string] A metric that shows how frobnicated your foos are + +If a user invokes `myi3stat` like this, your new metric will be displayed: + + myi3stat --your_metric "%f %f %d" +