Friday, April 1, 2011

SteelSeries JavaScript edition

Here we go again and it's again time for some canvas...
Those of you who followed this blog know that i started to port some of the components of the steelseries java library to html5 canvas. Because i'm not a javascript coder i had no idea how to build a library from these components and so i started playing around, trying this and that...
Finally i found a way that looks ok to me (but i might be wrong) and today i could present you the first version of the javascript version of the steelseries library (it only contains the Radial and RadialBargraph right now).

I tried to implement most of the features of the java version but right now there are still some feature missing.
Here is a list of the features that are supported by the javascript version:

GaugeType:

  • TYPE1
  • TYPE2
  • TYPE3
  • TYPE4


PointerType:

  • TYPE1
  • TYPE2
  • TYPE3
  • TYPE4
  • TYPE5
  • TYPE6
  • TYPE7
  • TYPE8

FrameDesign:

  • BLACK_METAL
  • METAL
  • SHINY_METAL
  • BRASS
  • STEEL
  • CHROME
  • GOLD


BackgroundColor:

  • DARK_GRAY
  • SATIN_GRAY
  • LIGHT_GRAY        
  • WHITE
  • BLACK
  • BEIGE
  • BROWN
  • RED
  • GREEN
  • BLUE


LcdColor:
  • BEIGE
  • BLUE
  • ORANGE
  • RED
  • YELLOW
  • WHITE
  • GRAY
  • BLACK
  • GREEN
  • BLUE2
  • BLUE_BLACK
  • BLUE_DARKBLUE
  • BLUE_GRAY
  • STANDARD
  • BLUE_BLUE
  • REDDARKRED


LedColor:
  • RED_LED
  • GREEN_LED
  • BLUE_LED
  • ORANGE_LED
  • YELLOW_LED
  • CYAN_LED
  • MAGENTA_LED


Color:
  • RED
  • GREEN
  • BLUE
  • ORANGE
  • YELLOW
  • CYAN        
  • MAGENTA
  • WHITE
  • GRAY
  • BLACK
  • RAITH
  • GREEN_LCD
  • JUG_GREEN


The Radial component also supports sections and areas. So there's no track right now (but it will come).

PREPARATION:
To make use of the library you have to add two files to your html page:

  • tween.js
  • steelseries.js

So a typical html5 page header will look like this...

e.g.

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8" />
    <title>Test</title>
    <script type='text/javascript' src='js/tween.js'></script>
    <script type='text/javascript' src='js/steelseries.js'></script>
...

USAGE:
To use the library you need to add a <canvas> tag for each gauge to the <body> of the page.

e.g.
...
<body onload='init()'>
    <canvas id='canvas1' width='200' height='200'>
        No canvas in your browser...sorry...
    </canvas>
    <canvas id='canvas2' width='200' height='200'></canvas>
<canvas id='canvas3' width='200' height='200'></canvas>
</body>
...
Now we only have to add the init() method in the <head> of the page, where we create the canvas components. !!! OLD VERSION !!!
function init()
{
  // Define some sections
  var sections = Array(steelseries.Section(0, 25, 'rgba(0, 0, 220, 0.3)'),
                       steelseries.Section(25, 50, 'rgba(0, 220, 0, 0.3)'), 
                       steelseries.Section(50, 75, 'rgba(220, 220, 0, 0.3)'));
  
  // Define one area
  var areas = Array(steelseries.Section(75, 100, 'rgba(220, 0, 0, 0.3)'));
            
  // Create one radial gauge
  var radial1 = new steelseries.Radial(
                    'canvas1',                              // the canvas element
                    steelseries.GaugeType.TYPE4,            // type of gauge
                    200,                                    // size of gauge
                    0,                                      // minimum value
                    100,                                    // maximum value
                    50,                                     // threshold
                    sections,                               // sections
                    areas,                                  // areas
                    'Test',                                 // title string
                    'Unit',                                 // unit string
                    steelseries.FrameDesign.METAL,          // frame design
                    steelseries.BackgroundColor.DARK_GRAY,  // background color
                    steelseries.PointerType.TYPE8,          // pointer type
                    steelseries.ColorDef.RED,               // pointer color
                    steelseries.LcdColor.STANDARD,          // lcd color
                    true,                                   // lcd visible
                    steelseries.LedColor.RED_LED,           // led color
                    true,                                   // led visible
                    false);                                 // play audio
  
  // Create a second radial gauge
  var radial2 = new steelseries.Radial(
                    'canvas2', 
                    steelseries.GaugeType.TYPE2, 
                    200, 
                    0, 
                    50, 
                    40, 
                    Array(steelseries.Section(0, 40, 'rgba(0, 255, 0, 0.3)')),
                    Array(steelseries.Section(40, 50, 'rgba(255, 0, 0, 0.5)')), 
                    'Test', 
                    'Unit', 
                    steelseries.FrameDesign.CHROME, 
                    steelseries.BackgroundColor.LIGHT_GRAY, 
                    steelseries.PointerType.TYPE2, 
                    steelseries.ColorDef.BLUE, 
                    steelseries.LcdColor.BLUE2, 
                    true, 
                    steelseries.LedColor.BLUE_LED, 
                    true, 
                    false);

  // Create a radial bargraph gauge
  var radial3 = new steelseries.RadialBargraph(
                    'canvas3',                               // the canvas element
                    steelseries.GaugeType.TYPE3,             // type of gauge
                    200,                                     // size of gauge
                    0,                                       // minimum value
                    100,                                     // maximum value
                    50,                                      // threshold
                    null,                                    // sections (not supported)
                    "Title",                                 // title string
                    "Unit",                                  // unit string
                    steelseries.FrameDesign.BLACK_METAL,     // frame design
                    steelseries.BackgroundColor.LIGHT_GRAY,  // background color 
                    steelseries.ColorDef.YELLOW,             // color of the bargraph led's
                    steelseries.LcdColor.YELLOW,             // lcd color
                    true,                                    // lcd visible
                    steelseries.LedColor.YELLOW_LED,         // led color
                    true);                                   // led visible

  // Let's set some values...
  radial1.setValueAnimated(70);
  radial2.setValueAnimated(41);
  radial3.setValueAnimated(70);
}

As you can see the drawback of the current design are the long constructors. I'm still not sure how to make these nicer but i'm working on that...


UPDATE:
Thanx to Andres Almiray who pointed me in the right direction i modified the constructor of the Radial and RadialBargraph component in the way that it now takes a hash as a set of parameters. This means you don't have to put in all the default parameters anymore which makes the initialization of the components look like this...
!!! NEW VERSION !!!


function init()
{
  // Define some sections
  var sections = Array(steelseries.Section(0, 25, 'rgba(0, 0, 220, 0.3)'),
                       steelseries.Section(25, 50, 'rgba(0, 220, 0, 0.3)'), 
                       steelseries.Section(50, 75, 'rgba(220, 220, 0, 0.3)'));
  
  // Define one area
  var areas = Array(steelseries.Section(75, 100, 'rgba(220, 0, 0, 0.3)'));
            
  // Create one radial gauge
  var radial1 = new steelseries.Radial(
                    'canvas1', {
                    section: sections,                      
                    area: areas,                            
                    titleString: 'Test',                    
                    unitString: 'Unit',                     
                    pointerType: steelseries.PointerType.TYPE8
                    });                               

// Create a second radial gauge
  var radial2 = new steelseries.Radial(
                    'canvas2', {
                    gaugeType: steelseries.GaugeType.TYPE2,                     
                    maxValue: 50, 
                    threshold: 40, 
                    section: Array(steelseries.Section(0,40,'rgba(0,255,0,0.3)')),
                    area: Array(steelseries.Section(40,50,'rgba(255,0,0,0.5)')), 
                    titleString: 'Test', 
                    unitString: 'Unit', 
                    frameDesign: steelseries.FrameDesign.CHROME, 
                    backgroundColor: steelseries.BackgroundColor.LIGHT_GRAY, 
                    pointerType: steelseries.PointerType.TYPE2, 
                    pointerColor: steelseries.ColorDef.BLUE, 
                    lcdColor: steelseries.LcdColor.BLUE2,                     
                    ledColor: steelseries.LedColor.BLUE_LED, 
                    });

  // Create a radial bargraph gauge
  var radial3 = new steelseries.RadialBargraph(
                    'canvas3', {
                    gaugeType: steelseries.GaugeType.TYPE3,
                    titleString: "Title",                                
                    unitString: "Unit",          
                    frameDesign: steelseries.FrameDesign.BLACK_METAL,
                    backgroundColor: steelseries.BackgroundColor.LIGHT_GRAY,
                    valueColor: steelseries.ColorDef.YELLOW,
                    lcdColor: steelseries.LcdColor.YELLOW,
                    ledColor: steelseries.LedColor.YELLOW_LED,
                    });                                   

  // Let's set some values...
  radial1.setValueAnimated(70);
  radial2.setValueAnimated(41);
  radial3.setValueAnimated(70);
}


Guess that looks much better than before... :-)




If you put all these things together in one html page you should see something like this...




If you are to lazy to play around you might want to click here to see it in action...


There are two versions of the library available right now, the uncompressed (101 kb) and compressed (61 kb) version. You could download the version clicking on one of the following links:


    uncompressed version:    steelseries.js


    compressed version:       steelseries-min.js


    animation library:           tween.js


Keep in mind that this project is work in progress and things might change in the future...


Enjoy the upcoming weekend and keep coding...

11 comments:

  1. Great Han!

    Its amazing work that you are coding! I'm learning amazing things following your project and this blog posts.

    Keep coding! Cya.

    ReplyDelete
  2. This comment has been removed by the author.

    ReplyDelete
  3. Hi, great work!

    We are using your components for data visualization and we need to be able to especify the animation configuration for each gauge.

    If possible, please consider using our patch for allowing custom tween functions and durations.

    Here is the patch:
    https://gist.github.com/1358801

    ReplyDelete
  4. Hi,

    is there a way to assign to the gauges the values stored in a txt file (which is updated every 5 minutes)?

    txt file example
    29/04/2012
    12:55:10
    15.4
    20.3
    00:13
    13.3
    11:10
    78
    94
    11:30
    50
    00:10
    11.6
    13.9
    12:22
    9.5
    00:10
    15.4
    13.3
    11:10
    15.4
    20.3
    00:13
    0.0
    30.6
    07:46
    0.0
    222
    SW
    1016.8
    +
    1017.1
    10:34
    1013.4
    06:26
    1.27
    1.02
    241.81
    328.93
    0.00
    2.29
    09:33
    n.d.

    regards

    Ugo

    ReplyDelete
    Replies
    1. Of course you can but that has nothing todo with the lib. I would suggest to google how to read and parse a textfile in JavaScript . If you know how to do that it should be no problem to set the values from your textfile to the gauges.
      Cheers,
      Gerrit

      Delete
  5. Hi Han,

    not sure if it is the right place to file a bug ticket for the JavaScript library.

    Every call of setMaxValue or setMinValue for an linearBargraph makes the light reflex (from the simulate glass above the gauge) above the title string a light lighter (or may be alpha value is increased). After a lets say 20-40 calls the white trapez is totally opaque.

    In the source code i found

    this.setMaxValue = function(value){
    if (maxValue !== value) {
    maxValue = value;
    init({background: true,
    foreground: true,
    pointer: true});
    this.repaint();
    }
    };

    since a call this function with "300" it works perfect for setting the max value - but the comparision with !== fails with executes init(...) on every call - the is of course my fault, but setMinValue has no comparison at all.

    ReplyDelete
    Replies
    1. I removed the check and it seems to work now (let it run for 30 min with 500ms updates and saw nothing disappears). If you still encounter problems, just let me know.
      Cheers,
      Gerrit

      Delete
    2. Oh, forgot to mention...please download the current version from the right side of this blog...

      Delete
  6. Hi,

    I am new to SteelSeries canvas gauges, I have managed to get it working by searching on the internet for clues.

    But is there somewhere that I can find out your current keywords you are using, as what I have found on the internet some are out of date and do not work.

    Thanks for the great gauges and look forward to using them in monitoring temperatures in my home central heating.

    Regards

    Gary

    ReplyDelete
    Replies
    1. Hi Gary,
      Sorry for the late reply, I think the easiest way to get all the available properties is to take a look at the source code. You could find it on github at https://github.com/HanSolo/SteelSeries-Canvas. If you look at the uncompressed version of the lib you will find all controls with their properties in that file.
      I hope that will help you...
      Cheers,
      Gerrit

      Delete
  7. Hi Han, you made a really great job and thank you for sharing your work to the world!
    I'm going to use your gauges to show data from my meteo station.

    Just a question: are you going to implement the wind rose in the javascript version?

    Regards,
    Vic

    ReplyDelete