Skip to content

Commit 2f58877

Browse files
author
Florian Hämmerle
committed
👋📊
0 parents  commit 2f58877

File tree

6 files changed

+172
-0
lines changed

6 files changed

+172
-0
lines changed

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
.DS_Store
2+
3+
node_modules

example.mjs

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
import { PlainChart } from ".";
2+
3+
//
4+
// simple bar chart
5+
//
6+
const chart = new PlainChart([1, 2, 3, 4, 5, 10, 7, 8, 0, 1, 4, 3], 10);
7+
console.log(chart.render());
8+
9+
//
10+
// sine wave
11+
//
12+
const values = range(0, 4 * Math.PI, 100).map(x => Math.sin(x) + 1.2);
13+
const chart2 = new PlainChart(values, 10, PlainChart.scatter);
14+
console.log(chart2.render());
15+
16+
function range(start, end, count) {
17+
const step = (end - start) / count;
18+
const values = [];
19+
for (let i = 0; i < count; i++) {
20+
values.push(start + i * step);
21+
}
22+
return values;
23+
}

license

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
MIT License
2+
3+
Copyright (c) 2018 BTD - Better Things Digital GmbH
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is
10+
furnished to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21+
SOFTWARE.

package.json

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
{
2+
"name": "@betterthings/plainchart",
3+
"version": "0.0.0",
4+
"description": "A text-based, no-dependencies, open-source charting utility in JavaScript.",
5+
"main": "plainchart.mjs",
6+
"keywords": [
7+
"chart",
8+
"plainchart",
9+
"plain",
10+
"text"
11+
],
12+
"author": {
13+
"name": "BTD - Better Things Digital GmbH",
14+
"email": "[email protected]",
15+
"url": "https://betterthings.digital"
16+
},
17+
"contributors": [
18+
{
19+
"name": "Florian Hämmerle",
20+
"email": "[email protected]"
21+
}
22+
],
23+
"license": "MIT"
24+
}

plainchart.mjs

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
export class PlainChart {
2+
constructor(values, height = 10, style) {
3+
if (height <= 0) {
4+
throw new Error("height must be above zero");
5+
}
6+
7+
this.values = values;
8+
this.height = height;
9+
this.max = Math.max(...values);
10+
11+
const columns = [];
12+
values.forEach(value => {
13+
const cells = [];
14+
for (let y = 1; y < this.height + 1; y += 1) {
15+
cells.push(
16+
style ? style(this, value, y) : PlainChart.bar(this, value, y)
17+
);
18+
}
19+
columns.push(cells);
20+
});
21+
22+
this.rows = [];
23+
for (let i = 0; i < this.height; i += 1) {
24+
this.rows.push(columns.map(c => c[i]));
25+
}
26+
this.rows = this.rows.reverse();
27+
}
28+
29+
y(value) {
30+
const _y = this.max != 0 ? Math.round((value * this.height) / this.max) : 0;
31+
return _y <= this.height ? _y : this.height;
32+
}
33+
34+
static bar(chart, value, y) {
35+
return y <= chart.y(value) ? "▌" : " ";
36+
}
37+
38+
static scatter(chart, value, y) {
39+
return y == chart.y(value) ? "×" : " ";
40+
}
41+
42+
render(newLine = "\n") {
43+
return this.rows.map(r => r.join("")).join(newLine);
44+
}
45+
}

readme.md

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
# PlainChart
2+
3+
A text-based, no-dependencies, open-source charting utility in JavaScript.
4+
It is inspired by the Python library [`plainchart`](https://github.com/gduverger/plainchart).
5+
6+
## Usage
7+
8+
```javascript
9+
import PlainChart from "@betterthings/plainchart";
10+
const chart = new PlainChart([3, 1, 4, 1, 5, 9, 2, 6, 5, 3, 5, 9]);
11+
console.log(chart.render());
12+
13+
/*
14+
15+
▌ ▌
16+
▌ ▌
17+
▌ ▌
18+
▌ ▌ ▌
19+
▌▌ ▌▌ ▌▌
20+
▌▌ ▌▌ ▌▌
21+
▌ ▌▌ ▌▌ ▌▌
22+
▌ ▌ ▌▌ ▌▌▌▌▌
23+
▌ ▌ ▌▌▌▌▌▌▌▌
24+
▌▌▌▌▌▌▌▌▌▌▌▌
25+
26+
*/
27+
```
28+
29+
Take a look at [`example.mjs`](example.mjs) to see how to generate something like this:
30+
31+
```
32+
×××××××× ××××××××
33+
××× ××× ××× ×××
34+
×× ×× ×× ××
35+
×× ×× ×× ××
36+
× × × ×
37+
× ×× ×× ×× ×
38+
×× ×× ×× ××
39+
×× ×× ×× ××
40+
××× ××× ××× ×××
41+
×××××××× ××××××××
42+
```
43+
44+
## Example
45+
46+
```sh
47+
node --experimental-modules example.mjs
48+
```
49+
50+
## Contribute
51+
52+
Please feel free to open an issue to propose a new feature or point out a bug. You can also fork the PlainChart repository and submit a pull request.
53+
54+
## Authors
55+
56+
- Florian Hämmerle ([@lusbuab](https://twitter.com/lusbuab)) - [Better Things Digital](https://betterthings.digital)

0 commit comments

Comments
 (0)