Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- const ws281x = require('rpi-ws281x-native');
- const EventEmitter = require('events');
- function parse(i, min, max) {
- const num = Number(i);
- if (isNaN((num))) {
- return min;
- }
- return Math.min(max, Math.max(min, num));
- }
- const DEFAULT_OPTIONS = {
- frequency: 700000,
- dmaNum: 10,
- gpioPin: 18,
- };
- const LED_MAX = 1000;
- class FastPixel extends EventEmitter {
- constructor() {
- super();
- this.ledCount = 1;
- this.pixelData = new Uint32Array(1);
- this.brightness = 100;
- this.timeout = null;
- this.initalized = false;
- }
- setLedCount(str) {
- const num = parse(str, 0, LED_MAX);
- if (this.ledCount === num) {
- return;
- }
- if (this.initalized) {
- this.clearAnimation();
- this.pixelData = null;
- ws281x.reset();
- }
- try {
- ws281x.init(num, DEFAULT_OPTIONS);
- this.ledCount = num;
- this.pixelData = new Uint32Array(num);
- this.initalized = true;
- } catch (e) {
- this.emit('error', e.message);
- }
- }
- setBrightness(percent) {
- const num = parse(percent, 0, 100);
- if (this.brightness === num) {
- return;
- }
- const brightness = Math.floor(num * 255 / 100);
- if (this.initalized) {
- try {
- ws281x.setBrightness(brightness);
- this.brightness = num;
- } catch (e) {
- this.emit('error', e.message);
- }
- }
- }
- clearAnimation() {
- if (this.timeout != null) {
- clearTimeout(this.timeout);
- this.timeout = null;
- }
- }
- rgb2Int(r, g, b) {
- return ((r & 0xff) << 16) + ((g & 0xff) << 8) + (b & 0xff);
- }
- setPixel(i, { r = 0, g = 0, b = 0 }) {
- this.pixelData[i] = this.rgb2Int(r, g, b);
- }
- render() {
- if (!this.initalized) {
- return;
- }
- try {
- ws281x.render(this.pixelData);
- } catch (e) {
- this.emit('error', e.message);
- }
- }
- animate(fn, time = 1000/30) {
- if (!this.initalized) {
- this.emit('error', 'The driver has not been initialized.');
- return;
- }
- this.clearAnimation();
- const execute = () => {
- const start = new Date();
- fn(this.pixelData, Math.floor(start / time));
- try {
- ws281x.render(this.pixelData);
- } catch (e) {
- this.emit('error', e.message);
- this.clearAnimation();
- }
- const elapsed = new Date() - start;
- if (elapsed < time) {
- this.timeout = setTimeout(execute, time - elapsed);
- } else {
- this.emit('warn', `animation loop ran long ${elapsed}ms`);
- execute();
- }
- };
- execute();
- }
- }
- module.exports = new FastPixel();
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement