Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/romrider/node-divoom-timebox-evo
A node module to generate messages for the Divoom Timebox Evo compatible with the module bluetooth-serial-port (https://github.com/eelcocramer/node-bluetooth-serial-port)
https://github.com/romrider/node-divoom-timebox-evo
divoom evo node node-module nodejs timebox
Last synced: 31 minutes ago
JSON representation
A node module to generate messages for the Divoom Timebox Evo compatible with the module bluetooth-serial-port (https://github.com/eelcocramer/node-bluetooth-serial-port)
- Host: GitHub
- URL: https://github.com/romrider/node-divoom-timebox-evo
- Owner: RomRider
- License: mit
- Created: 2019-08-27T18:03:17.000Z (about 5 years ago)
- Default Branch: master
- Last Pushed: 2022-12-30T18:31:49.000Z (almost 2 years ago)
- Last Synced: 2024-11-09T19:47:07.779Z (8 days ago)
- Topics: divoom, evo, node, node-module, nodejs, timebox
- Language: TypeScript
- Homepage:
- Size: 1.1 MB
- Stars: 136
- Watchers: 6
- Forks: 16
- Open Issues: 17
-
Metadata Files:
- Readme: README.md
- License: LICENSE.md
Awesome Lists containing this project
README
# node-divoom-timebox-evo
This module helps you generate the appropriate message to use against the divoom timebox evo.
The communication part is not implemented here and you can use the [bluetooth-serial-port](https://github.com/eelcocramer/node-bluetooth-serial-port) module to communicate with the timebox.
Here's how you could do it:
```js
const TIMEBOX_ADDRESS = "11:22:33:44:55:66";
var btSerial = new (require('bluetooth-serial-port')).BluetoothSerialPort();
var Divoom = require('node-divoom-timebox-evo');btSerial.findSerialPortChannel(TIMEBOX_ADDRESS, function(channel) {
btSerial.connect(address, channel, function() {
console.log('connected');btSerial.on('data', function(buffer) {
console.log(buffer.toString('ascii'));
});
}, function () {
console.log('cannot connect');
});
}, function() {
console.log('found nothing');
});var d = (new Divoom.TimeboxEvo()).createRequest('animation');
d.read('animation.gif').then(result => {
result.asBinaryBuffer().forEach(elt => {
btSerial.write(elt,
function(err, bytesWritten) {
if (err) console.log(err);
}
);
})
}).catch(err => {
throw err;
});```
# Protocol Documentation
See [Protocol](PROTOCOL.md)
# Install
```sh
npm i node-divoom-timebox-evo
```# Some Examples
See the complete documentation [here](https://romrider.github.io/node-divoom-timebox-evo/docs/)
## Create a request
You'll always have to create a request first:
```js
var Divoom = require('node-divoom-timebox-evo');
var d = (new Divoom.TimeboxEvo()).createRequest('REQUEST_TYPE');// d.messages.asBinaryBuffer() is an array of messages you have to send to your Timebox Evo over bluetooth as is. It returns an array of Buffers with Binary content.
console.log(d.messages.asBinaryBuffer());
```The different `REQUEST_TYPE` are:
* `cloud`: Will interact with the [Cloud Channel](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/cloudchannel.html)
* `custom`: Will interact with the [Custom Channel](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/customchannel.html)
* `lightning`: Will interact with the [Lightning Channel](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/lightningchannel.html)
* `scoreboard`: Will interact with the [Scoreboard](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/scoreboardchannel.html)
* `time`: Will interact with the [Time Channel](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/timechannel.html)
* `vjeffect`: Will interact with the [VJ Effect Channel](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/vjeffectchannel.html)
* `brightness`: Will set the [brightness](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/brightnesscommand.html)
* `temp_weather`: Will set the [temperature and the weather](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/tempweathercommand.html)
* `text`: Will display some [text](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/displaytext.html)
* `picture` or `animation`: Will display a [picture or an animation](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/displayanimation.html)
* `raw`: To send a [RAW](https://romrider.github.io/node-divoom-timebox-evo/docs/classes/timeboxevorequest.html) command## RAW Command
There's no need to calculate the size or the CRC of the messages. This will be done automatically.
```js
var Divoom = require('node-divoom-timebox-evo');var d = (new Divoom.TimeboxEvo()).createRequest('raw');
d.push("4505");
d.messages.forEach(m => {
console.log(m.message);
}) // Will display the list of messages as hexadecimals strings
console.log(d.messages.asBinaryBuffer());
```## Displaying an animation or a picture
```js
var Divoom = require('node-divoom-timebox-evo');var d = (new Divoom.TimeboxEvo()).createRequest('animation');
d.read('file.png').then(result => {
console.log(result.asBinaryBuffer());
// send toSend to the Divoom
// use https://github.com/eelcocramer/node-bluetooth-serial-port
}).catch(err => {
throw err;
});
```## Displaying Text
You have a number of baked in palettes:
* `PALETTE_TEXT_ON_BACKGROUND(text?: ColorInput, background?: ColorInput)`: Sets the text color and the background color
* `PALETTE_BLACK_ON_RAINBOW`: Black text on a rainbow background
* `PALETTE_BLACK_ON_CMY_RAINBOW`: Black text on a CMY rainbow backgroundAnd a number of baked in animations:
* `ANIM_STATIC_BACKGROUND`: Background will not change color (useful with `PALETTE_TEXT_ON_BACKGROUND`)
* `ANIM_UNI_GRADIANT_BACKGROUND`: Uniform background which will loop over all the colors of your palette
* `ANIM_VERTICAL_GRADIANT_BACKGROUND`: Vertical gradient background which will loop over all the colors of your palette
* `ANIM_HORIZONTAL_GRADIANT_BACKGROUND`: Horizontal gradient background which will loop over all the colors of your palette```js
var Divoom = require('node-divoom-timebox-evo');var d = (new Divoom.TimeboxEvo()).createRequest('text', {text: "Hi friends!"});
d.paletteFn = d.PALETTE_BLACK_ON_CMY_RAINBOW; // Baked in color palette, but you can define your own
d.animFn = d.ANIM_HORIZONTAL_GRADIANT_BACKGROUND; // Baked in animation, but you can define your own// This contains what is required to bootstrap the display on the Timebox
console.log(d.messages.asBinaryBuffer());// Then you have to send your animation frame by frame, I suggest that you do no go over 30 message per second, if you do, the timebox will disconnect.
// This would generate 512 animation frames.
for (i = 0; i < 512; i++){
console.log(d.getNextAnimationFrame().asBinaryBuffer());
}
```You can define your own palette, the function has to return an array of 256 colors in Hex.
The text's color will be the item `(background_color + 127) % 256`.
This is the code which generates the `PALETTE_BLACK_ON_RAINBOW`:
```typescript
d.paletteFn = function() {
function number2HexString(int: number): string {
return Math.round(int).toString(16).padStart(2, "0");
}let palette: string[] = [];
const size = 127;
function sin_to_hex(i: number, phase: number) {
let sin = Math.sin(Math.PI / size * 2 * i + phase);
let int = Math.floor(sin * 127) + 128;
return number2HexString(int);
}for (let i = 0; i < size; i++) {
let red = sin_to_hex(i, 0 * Math.PI * 2 / 3); // 0 deg
let blue = sin_to_hex(i, 1 * Math.PI * 2 / 3); // 120 deg
let green = sin_to_hex(i, 2 * Math.PI * 2 / 3); // 240 deg
palette.push(red + green + blue);
}// Completes the palette (everything after the 127th item in the array) with black color so that the text is actually only black
for (let i = palette.length; i < 256; i++) {
palette.push("000000");
}
return palette;
}
```You can also define your own animation. It should be an array of 256 entries each one representing a pixel and referencing the index of the color to be displayed, taken from the palette. The function takes a frame number as a parameter.
Example which generated the horizontal gradient background (`ANIM_HORIZONTAL_GRADIANT_BACKGROUND`):
```typescript
d.animFn = function(frame) {
let pixelArray = [];
for (let y = 0; y < 16; y++) {
for (let x = 0; x < 16; x++) {
pixelArray.push((x + frame) % 127)
}
}
return pixelArray;
}
```