.. index::
   single: STYLEITEM Javascript

.. _styleitemjs:

*****************************************************************************
 STYLEITEM Javascript
*****************************************************************************

:Author:        Charles-Éric Bourget
:Contact:       cbourget at mapgears.com
:Author:        Alan Boudreault
:Contact:       aboudreault at mapgears.com
:Last Updated: 2015-05-21

.. contents:: Table of Contents
    :depth: 2
    :backlinks: top

Introduction
---------------------------------------------
Using STYLEITEM this way makes it possible to style
features programmatically rather than with the standard
MapServer expressions.

Usage
---------------------------------------------
Simply declare the javascript plugin this way:

.. code-block:: mapfile

  MAP
    ...
    LAYER
    ...
      STYLEITEM "javascript://myscript.js" # relative path
      CLASS
      END
    END
  END

The path can also be absolute.

.. code-block:: mapfile

  MAP
    ...
    LAYER
    ...
      STYLEITEM "javascript:///home/user/myscript.js" # absolute path
      CLASS
      END
    END
  END

The javascript plugin has to implement a function named **styleitem** that will
be automatically called. This function has to return one of these two options:

- a STYLE definition (Plain String)
- a CLASS definition with one or multiple styles (Plain String)

.. note::
  Features are parsed one at a time and each one makes a call
  to the javascript plugin. That means the STYLE or CLASS
  returned is applied to that specific feature only. Therefore,
  a CLASS block should not contain an EXPRESSION definition
  and the corresponding LAYER should not contain a CLASSITEM
  definition.

.. note::
  Declaring an empty CLASS is mandatory

Access to the feature attributes is made through the
``shape.attributes`` javascript object.

The following javascript functions are available:

- alert(str1, str2, ..., str)
    print some text in MapServer logs
- print(str1, str2, ..., str)
    print some text in MapServer logs
- require(path_to_lib1, path_to_lib2, ..., path_to_lib)
    include one or more javascript lib

Example 1. Single STYLE definition
---------------------------------------------
This example returns a single STYLE definition ...

.. code-block:: javascript

  function styleitem() {
    //Make symbol size 14 or 7
    var size = shape.attributes.NAME.length > 10 ? 14:7;

    var style = "STYLE SIZE " + size + " SYMBOL 'circle'";

    var red = Math.random()*255;
    var green = Math.random()*255;
    var blue = Math.random()*255;
    style += "COLOR " + red + " " + green + " " + blue + " END";

    //Return style to MapServer
    return style;
  }

Example 2. CLASS with multiple STYLE definitions
------------------------------------------------

This example returns a single CLASS with multiple
STYLE definitions ...

.. code-block:: javascript

  function styleitem() {
    var cls = "CLASS";

    //Make symbol size 14 or 7
    var size = shape.attributes.NAME.length > 10 ? 14:7;

    var style1 = "STYLE SIZE " + size + " SYMBOL 'circle'";
    var style2 = "STYLE SIZE " + size + " SYMBOL 'cross'";

    var red = Math.random()*255;
    var green = Math.random()*255;
    var blue = Math.random()*255;
    style1 += "COLOR " + red + " " + green + " " + blue + " END";
    style2 += "COLOR " + red + " " + green + " " + blue + " END";

    cls += " " + style1 + " " + style2 + " END";

    //Return class to MapServer
    return cls;
  }

Example 3. Printing logs in MapServer logs
---------------------------------------------
This example prints some javascript logs in
MapServer logs.

.. code-block:: mapfile

  MAP
    ...
    CONFIG  "MS_ERRORFILE" "/tmp/mapserver.log"
    DEBUG 1
    LAYER
    ...
      STYLEITEM "javascript://myscript.js"
      CLASS
      END
    END
  END

.. code-block:: javascript

  function styleitem() {
    //Print some logs in MapServer logs
    alert("Processing feature " + shape.attributes.NAME)

    //Make symbol size 14 or 7
    var size = shape.attributes.NAME.length > 10 ? 14:7;

    var style = "STYLE SIZE " + size + " SYMBOL 'circle'";

    var red = Math.random()*255;
    var green = Math.random()*255;
    var blue = Math.random()*255;
    style += "COLOR " + red + " " + green + " " + blue + " END";

    //Return style to MapServer
    return style;
  }
