Added Item::scaleInPoint

Added Item::scaleInPoint

# Item

    'use strict'

    assert = require 'src/assert'
    utils = require 'src/utils'
    signal = require 'src/signal'
    List = require 'src/list'

    {isArray} = Array
    {emitSignal} = signal.Emitter

    assert = assert.scope 'Renderer.Item'

    module.exports = (Renderer, Impl, itemUtils) -> class Item extends itemUtils.Object
        @__name__ = 'Item'
        @__path__ = 'Renderer.Item'

        Document = require 'src/document'
        DocElement = Document.Element

## *Item* Item.New([*Object* options])

        @New = (opts) ->
            item = new Item
            itemUtils.Object.initialize item, opts
            item

## *Item* Item::constructor()

This is a base class for everything which is visible.

        constructor: ->
            assert.instanceOf @, Item

            super()
            @_parent = null
            @_children = null
            @_previousSibling = null
            @_nextSibling = null
            @_belowSibling = null
            @_aboveSibling = null
            @_width = 0
            @_height = 0
            @_x = 0
            @_y = 0
            @_z = 0
            @_visible = true
            @_clip = false
            @_scale = 1
            @_rotation = 0
            @_opacity = 1
            @_linkUri = ''
            @_anchors = null
            @_layout = null
            @_keys = null
            @_pointer = null
            @_margin = null
            @_classes = null
            @_query = ''
            @_node = null

### Custom properties

```nml
Item {
    id: main
    property currentLife: 0.8
    Text {
        text: "Life: " + main.currentLife
    }
}
```

### Custom signals

```nml
Item {
    signal onPlayerCollision
    onPlayerCollision(){
        // boom!
    }
}
```

## ReadOnly *String* Item::query

        utils.defineProperty @::, 'query', null, ->
            @_query
        , (val) ->
            if @_query is ''
                @_query = val
            return

## ReadOnly *Document.Element* Item::node

## *Signal* Item::onNodeChange(*Document.Element* oldValue)

```javascript
Text {
    text: this.node.props.value
}
```

```javascript
Text {
    onNodeChange: function(){
        var inputs = this.node.queryAll('input[type=string]');
    }
}
```

        itemUtils.defineProperty
            constructor: @
            name: 'node'
            defaultValue: null
            developmentSetter: (val) ->
                if val?
                    assert.instanceOf val, DocElement

## *Signal* Item::ready()

Called when the Item is ready, that is, all
properties have been set and it's ready to use.

```nml
Rectangle {
    width: 200
    height: 50
    color: 'green'
    Rectangle {
        width: parent.width / 2
        height: parent.height / 2
        color: 'yellow'
        onReady: function(){
            console.log(this.width, this.height);
            // 100, 25
        }
    }
}
```

        signal.Emitter.createSignal @, 'onReady'

## *Signal* Item::onAnimationFrame(*Integer* miliseconds)

        signal.Emitter.createSignal @, 'onAnimationFrame', do ->
            now = Date.now()
            items = []

            frame = ->
                oldNow = now
                now = Date.now()
                ms = now - oldNow

                for item in items
                    emitSignal item, 'onAnimationFrame', ms
                requestAnimationFrame frame

            requestAnimationFrame? frame

            (item) ->
                items.push item

## ReadOnly *String* Item::id

## *Object* Item::children

        utils.defineProperty @::, 'children', null, ->
            @_children ||= new ChildrenObject(@)
        , (val) ->
            assert.isArray val, "Item.children needs to be an array, but #{val} given"
            @clear()
            for item in val
                val.parent = @
            return

## *Signal* Item::onChildrenChange(*Item* added, *Item* removed)

        signal.Emitter.createSignal @, 'onChildrenChange'

        class ChildrenObject extends itemUtils.MutableDeepObject
            constructor: (ref) ->
                @_layout = null
                @_target = null
                @_firstChild = null
                @_lastChild = null
                @_bottomChild = null
                @_topChild = null
                @_length = 0
                super ref

### ReadOnly *Item* Item::children.firstChild

            utils.defineProperty @::, 'firstChild', null, ->
                @_firstChild
            , null

### ReadOnly *Item* Item::children.lastChild

            utils.defineProperty @::, 'lastChild', null, ->
                @_lastChild
            , null

### ReadOnly *Item* Item::children.bottomChild

            utils.defineProperty @::, 'bottomChild', null, ->
                @_bottomChild
            , null

### ReadOnly *Item* Item::children.topChild

            utils.defineProperty @::, 'topChild', null, ->
                @_topChild
            , null

### ReadOnly *Integer* Item::children.length

            utils.defineProperty @::, 'length', null, ->
                @_length
            , null

### *Item* Item::children.layout

Item used to position children items.
Can be e.g. *Flow*, *Grid* etc.

### *Signal* Item::children.onLayoutChange(*Item* oldValue)

            itemUtils.defineProperty
                constructor: @
                name: 'layout'
                defaultValue: null
                developmentSetter: (val) ->
                    if val?
                        assert.instanceOf val, Item, """
                            Item.children.layout needs to be an Item, but #{val} given
                        """
                setter: (_super) -> (val) ->
                    if @_layout?.effectItem
                        @_layout.parent = null
                        @_layout.effectItem = @_layout

                    _super.call @, val

                    if '_effectItem' of @_ref
                        @_ref.effectItem = if val then null else @_ref

                    if val?
                        ref = @_ref
                        setFakeParent val, ref, 0
                        if val.effectItem
                            val.effectItem = ref

                    return

### *Item* Item::children.target

A new child trying to be added into the item with the `children.target` defined
will be added into the `target` item.

### *Signal* Item::children.onTargetChange(*Item* oldValue)

            itemUtils.defineProperty
                constructor: @
                name: 'target'
                defaultValue: null
                developmentSetter: (val) ->
                    if val?
                        assert.instanceOf val, Item, """
                            Item.children.target needs to be an Item, but #{val} given
                        """

### *Item* Item::children.get(*Integer* index)

Returns an item with the given index.

            get: (val) ->
                assert.operator val, '>=', 0, """
                    Item.children.get index cannot be lower than zero, #{val} given
                """
                assert.operator val, '<', @length, """
                    Item.children.get index must be lower than children.length, \
                    #{val} given
                """

                if val < @length / 2
                    sibling = @firstChild
                    while val > 0
                        sibling = sibling.nextSibling
                        val--
                else
                    sibling = @lastChild
                    while val > 0
                        sibling = sibling.previousSibling
                        val--

                sibling

### *Integer* Item::children.index(*Item* value)

Returns an index of the given child in the children array.

            index: (val) ->
                if @has(val)
                    val.index
                else
                    -1

### *Boolean* Item::children.has(*Item* value)

Returns `true` if the given item is an item child.

            has: (val) ->
                @_ref is val._parent

### Item::children.clear()

Removes all children from the item.

            clear: ->
                while last = @last
                    last.parent = null
                return

## *Item* Item::parent = `null`

## *Signal* Item::onParentChange(*Item* oldParent)

        setFakeParent = (child, parent, index=-1) ->
            child.parent = null

            if index >= 0 and parent.children._length < index
                Impl.insertItemBefore.call child, parent.children[index]
            else
                Impl.setItemParent.call child, parent

            child._parent = parent
            emitSignal child, 'onParentChange', null
            return

        updateZSiblingsForAppendedItem = (item, z, newChildren) ->
            child = newChildren._topChild
            while child
                if child._z <= z
                    if item._aboveSibling = child._aboveSibling
                        item._aboveSibling._belowSibling = item
                    item._belowSibling = child
                    child._aboveSibling = item
                    return
                unless nextChild = child._belowSibling
                    item._aboveSibling = child
                    child._belowSibling = item
                    item._belowSibling = null
                    return
                child = nextChild
            return

        insertItemInImpl = (item) ->
            if aboveSibling = item._aboveSibling
                Impl.insertItemBefore.call item, aboveSibling
            else
                Impl.setItemParent.call item, item._parent
            return

        itemUtils.defineProperty
            constructor: @
            name: 'parent'
            defaultValue: null
            setter: (_super) -> (val = null) ->
                old = @_parent
                oldChildren = old?.children
                valChildren = val?.children

                if valChildren?._target
                    # detect whether target is a child of this item
                    containsItem = false
                    tmpItem = valChildren._target
                    while tmpItem
                        if tmpItem is @
                            containsItem = true
                            break
                        tmpItem = tmpItem._parent

                    unless containsItem
                        val = valChildren._target
                        valChildren = val.children

                if old is val
                    return

                assert.isNot @, val, "Item.parent cannot be set with context item, #{val} given"

                if pointer = @_pointer
                    pointer.hover = pointer.pressed = false

                if val isnt null
                    assert.instanceOf val, Item, """
                        Item.parent needs to be an Item or null, but #{val} given
                    """

                # old siblings
                oldPreviousSibling = @_previousSibling
                oldNextSibling = @_nextSibling
                if oldPreviousSibling isnt null
                    oldPreviousSibling._nextSibling = oldNextSibling
                if oldNextSibling isnt null
                    oldNextSibling._previousSibling = oldPreviousSibling

                # new siblings
                if val isnt null
                    if previousSibling = @_previousSibling = valChildren.lastChild
                        previousSibling._nextSibling = @
                else
                    @_previousSibling = null
                if oldNextSibling isnt null
                    @_nextSibling = null

                # children
                if oldChildren
                    oldChildren._length -= 1
                    if oldChildren.firstChild is @
                        oldChildren._firstChild = oldNextSibling
                    if oldChildren.lastChild is @
                        oldChildren._lastChild = oldPreviousSibling
                if valChildren
                    if ++valChildren._length is 1
                        valChildren._firstChild = @
                    valChildren._lastChild = @

                # old z-index siblings
                oldBelowSibling = @_belowSibling
                oldAboveSibling = @_aboveSibling
                if oldBelowSibling isnt null
                    oldBelowSibling._aboveSibling = oldAboveSibling
                if oldAboveSibling isnt null
                    oldAboveSibling._belowSibling = oldBelowSibling

                # new z-index siblings
                @_belowSibling = @_aboveSibling = null
                if valChildren
                    updateZSiblingsForAppendedItem @, @_z, valChildren

                # z-index children
                if oldChildren
                    unless oldAboveSibling
                        oldChildren._topChild = oldBelowSibling
                    unless oldBelowSibling
                        oldChildren._bottomChild = oldAboveSibling
                if valChildren
                    unless @_aboveSibling
                        valChildren._topChild = @
                    unless @_belowSibling
                        valChildren._bottomChild = @

                # parent
                @_parent = val
                insertItemInImpl @

                `//<development>`
                assert.is @nextSibling, null
                if val
                    assert.is val.children.lastChild, @
                    assert.isDefined val.children.firstChild
                    assert.isDefined val.children.lastChild
                    assert.isDefined val.children.topChild
                    assert.isDefined val.children.bottomChild
                if old and old.children.length is 0
                    assert.isNotDefined old.children.firstChild
                    assert.isNotDefined old.children.lastChild
                    assert.isNotDefined old.children.topChild
                    assert.isNotDefined old.children.bottomChild
                `//</development>`

                # signals
                if old isnt null
                    emitSignal old, 'onChildrenChange', null, @
                if val isnt null
                    emitSignal val, 'onChildrenChange', @, null

                emitSignal @, 'onParentChange', old

                if oldPreviousSibling isnt null
                    emitSignal oldPreviousSibling, 'onNextSiblingChange', @
                if oldNextSibling isnt null
                    emitSignal oldNextSibling, 'onPreviousSiblingChange', @

                if val isnt null or oldPreviousSibling isnt null
                    if previousSibling
                        emitSignal previousSibling, 'onNextSiblingChange', null
                    emitSignal @, 'onPreviousSiblingChange', oldPreviousSibling
                if oldNextSibling isnt null
                    emitSignal @, 'onNextSiblingChange', oldNextSibling

                return

## *Item* Item::previousSibling

        utils.defineProperty @::, 'previousSibling', null, ->
            @_previousSibling
        , (val = null) ->
            assert.isNot @, val, """
                Item.previousSibling cannot be set with context Item, #{val} given
            """

            if val is @_previousSibling
                return

            if val
                assert.instanceOf val, Item, """
                    Item.previousSibling must be an Item or null, but #{val} given
                """
                nextSibling = val._nextSibling
                if not nextSibling and val._parent isnt @_parent
                    @parent = val._parent
                else
                    @nextSibling = nextSibling
            else
                assert.isDefined @_parent, """
                    Cannot null Item.previousSibling when Item has no parent
                """
                @nextSibling = @_parent.children.firstChild

            assert.is @_previousSibling, val
            return

## *Signal* Item::onPreviousSiblingChange(*Item* oldValue)

        signal.Emitter.createSignal @, 'onPreviousSiblingChange'

## *Item* Item::nextSibling

        isNextSibling = (item, sibling) ->
            while item
                nextItem = item._nextSibling
                if nextItem is sibling
                    return true
                item = nextItem
            return false

        isPreviousSibling = (item, sibling) ->
            while item
                prevItem = item._previousSibling
                if prevItem is sibling
                    return true
                item = prevItem
            return false

        updateZSiblingsForInsertedItem = (item, nextSibling, z, newChildren) ->
            if nextSibling._z is z
                # simple case - the same z-index as in nextSibling
                if item._belowSibling = nextSibling._belowSibling
                    item._belowSibling._aboveSibling = item
                item._aboveSibling = nextSibling
                nextSibling._belowSibling = item
            else
                # hard case - different z-indexes
                nextChild = newChildren._bottomChild
                while child = nextChild
                    nextChild = child._aboveSibling
                    if child._z > z or (child._z is z and isNextSibling(item, child))
                        item._aboveSibling = child
                        if item._belowSibling = child._belowSibling
                            item._belowSibling._aboveSibling = item
                        child._belowSibling = item
                        break
                    unless nextChild
                        item._aboveSibling = null
                        item._belowSibling = child
                        child._aboveSibling = item
            return

        utils.defineProperty @::, 'nextSibling', null, ->
            @_nextSibling
        , (val = null) ->
            assert.isNot @, val, """
                Item.nextSibling cannot be set with context Item, #{val} given
            """
            if val
                assert.instanceOf val, Item, """
                    Item.nextSibling needs to be an Item or null, but #{val} given
                """
                assert.isDefined val._parent, """
                    Item.nextSibling value needs to have a parent, given #{val} has no parent
                """
            else
                assert.isDefined @_parent, """
                    Cannot null Item.nextSibling when Item has no parent
                """

            if val is @_nextSibling
                return

            oldParent = @_parent
            oldChildren = oldParent?._children
            oldPreviousSibling = @_previousSibling
            oldNextSibling = @_nextSibling

            if val
                newParent = val._parent
                newChildren = newParent._children
            else
                newParent = oldParent
                newChildren = oldChildren

            # new parent
            @_parent = newParent

            # current siblings
            oldPreviousSibling?._nextSibling = oldNextSibling
            oldNextSibling?._previousSibling = oldPreviousSibling

            # new siblings
            previousSibling = previousSiblingOldNextSibling = null
            nextSibling = nextSiblingOldPreviousSibling = null
            if val
                if previousSibling = val._previousSibling
                    previousSiblingOldNextSibling = previousSibling._nextSibling
                    previousSibling._nextSibling = @

                nextSibling = val
                nextSiblingOldPreviousSibling = nextSibling._previousSibling
                nextSibling._previousSibling = @
            else
                if previousSibling = newChildren.lastChild
                    previousSibling._nextSibling = @

            @_previousSibling = previousSibling
            @_nextSibling = nextSibling

            # children
            if oldChildren
                oldChildren._length -= 1
                unless oldPreviousSibling
                    oldChildren._firstChild = oldNextSibling
                unless oldNextSibling
                    oldChildren._lastChild = oldPreviousSibling
            newChildren._length += 1
            if newChildren.firstChild is val
                newChildren._firstChild = @
            unless val
                newChildren._lastChild = @

            # old z-index siblings
            oldBelowSibling = @_belowSibling
            oldAboveSibling = @_aboveSibling
            if oldBelowSibling isnt null
                oldBelowSibling._aboveSibling = oldAboveSibling
            if oldAboveSibling isnt null
                oldAboveSibling._belowSibling = oldBelowSibling

            # new z-index siblings
            @_belowSibling = @_aboveSibling = null
            if nextSibling
                updateZSiblingsForInsertedItem @, nextSibling, @_z, newChildren
            else
                updateZSiblingsForAppendedItem @, @_z, newChildren

            # z-index children
            if oldChildren
                unless oldAboveSibling
                    oldChildren._topChild = oldBelowSibling
                unless oldBelowSibling
                    oldChildren._bottomChild = oldAboveSibling
            unless @_aboveSibling
                newChildren._topChild = @
            unless @_belowSibling
                newChildren._bottomChild = @

            # implementation
            insertItemInImpl @

            `//<development>`
            assert.is @_nextSibling, val
            assert.is @_parent, newParent
            if val
                assert.is @_parent, val._parent
            if @_previousSibling
                assert.is @_previousSibling._nextSibling, @
            if @_nextSibling
                assert.is @_nextSibling._previousSibling, @
            if oldPreviousSibling
                assert.is oldPreviousSibling._nextSibling, oldNextSibling
            if oldNextSibling
                assert.is oldNextSibling._previousSibling, oldPreviousSibling
            `//</development>`

            # children signal
            if oldParent isnt newParent
                if oldParent
                    emitSignal oldParent, 'onChildrenChange', null, @
                emitSignal newParent, 'onChildrenChange', @, null
                emitSignal @, 'onParentChange', oldParent
            else
                emitSignal newParent, 'onChildrenChange', null, null

            # current siblings signals
            if oldPreviousSibling
                emitSignal oldPreviousSibling, 'onNextSiblingChange', @
            if oldNextSibling
                emitSignal oldNextSibling, 'onPreviousSiblingChange', @

            # new siblings signals
            emitSignal @, 'onPreviousSiblingChange', oldPreviousSibling
            if previousSibling
                emitSignal previousSibling, 'onNextSiblingChange', previousSiblingOldNextSibling
            emitSignal @, 'onNextSiblingChange', oldNextSibling
            if nextSibling
                emitSignal nextSibling, 'onPreviousSiblingChange', nextSiblingOldPreviousSibling

            return

## *Signal* Item::onNextSiblingChange(*Item* oldValue)

        signal.Emitter.createSignal @, 'onNextSiblingChange'

## ReadOnly *Item* Item::belowSibling

        utils.defineProperty @::, 'belowSibling', null, ->
            @_belowSibling
        , null

## ReadOnly *Item* Item::aboveSibling

        utils.defineProperty @::, 'aboveSibling', null, ->
            @_aboveSibling
        , null

## *Integer* Item::index

        utils.defineProperty @::, 'index', null, ->
            index = 0
            sibling = @
            while sibling = sibling.previousSibling
                index++
            index
        , (val) ->
            assert.isInteger val, "Item.index needs to be a integer, but #{val} given"
            assert.isDefined @_parent, """
                When setting Item.index, item needs to have a parent, #{@} has no parent
            """
            assert.operator val, '>=', 0, "Item.index needs to greater than zero, #{val} given"
            assert.operator val, '<=', @_parent._children.length, """
                Item.index needs to be lower than parent.children.length, #{val} given
            """

            {children} = @parent
            if val >= children.length
                @nextSibling = null
            else if (valItem = children.get(val)) isnt @
                @nextSibling = valItem

            return

## *Boolean* Item::visible = `true`

Determines whether an item is visible or not.

```nml
Item {
    width: 100
    height: 100
    pointer.onClick: function(){
        rect.visible = !rect.visible;
        text.text = rect.visible ? "Click to hide" : "Click to show";
    }
    Rectangle {
        id: rect
        anchors.fill: parent
        color: 'blue'
    }
    Text {
        id: text
        text: "Click to hide"
        anchors.centerIn: parent
    }
}
```

## *Signal* Item::onVisibleChange(*Boolean* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'visible'
            defaultValue: true
            implementation: Impl.setItemVisible
            developmentSetter: (val) ->
                assert.isBoolean val, "Item.visible needs to be a boolean, but #{val} given"

## *Boolean* Item::clip = `false`

## *Signal* Item::onClipChange(*Boolean* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'clip'
            defaultValue: false
            implementation: Impl.setItemClip
            developmentSetter: (val) ->
                assert.isBoolean val, "Item.clip needs to be a boolean, but #{val} given"

## *Float* Item::width = `0`

## *Signal* Item::onWidthChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'width'
            defaultValue: 0
            implementation: Impl.setItemWidth
            developmentSetter: (val) ->
                assert.isFloat val, "Item.width needs to be a float, but #{val} given"

## *Float* Item::height = `0`

## *Signal* Item::onHeightChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'height'
            defaultValue: 0
            implementation: Impl.setItemHeight
            developmentSetter: (val) ->
                assert.isFloat val, "Item.height needs to be a float, but #{val} given"

## *Float* Item::x = `0`

## *Signal* Item::onXChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'x'
            defaultValue: 0
            implementation: Impl.setItemX
            developmentSetter: (val) ->
                assert.isFloat val, "Item.x needs to be a float, but #{val} given"

## *Float* Item::y = `0`

## *Signal* Item::onYChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'y'
            defaultValue: 0
            implementation: Impl.setItemY
            developmentSetter: (val) ->
                assert.isFloat val, "Item.y needs to be a float, but #{val} given"

## *Float* Item::z = `0`

## *Signal* Item::onZChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'z'
            defaultValue: 0
            developmentSetter: (val) ->
                assert.isFloat val, "Item.z needs to be a float, but #{val} given"
            setter: (_super) -> (val) ->
                oldVal = @_z
                if oldVal is val
                    return

                _super.call @, val

                unless parent = @_parent
                    return
                children = parent._children
                oldAboveSibling = @_aboveSibling
                oldBelowSibling = @_belowSibling

                # new siblings
                if val > oldVal
                    nextChild = @_aboveSibling
                    while child = nextChild
                        nextChild = child._aboveSibling
                        if child._z > val or (child._z is val and isNextSibling(@, child))
                            if oldAboveSibling is child
                                break
                            @_aboveSibling = child
                            if @_belowSibling = child._belowSibling
                                @_belowSibling._aboveSibling = @
                            child._belowSibling = @
                            break
                        unless nextChild
                            @_aboveSibling = null
                            @_belowSibling = child
                            child._aboveSibling = @

                if val < oldVal
                    prevChild = @_belowSibling
                    while child = prevChild
                        prevChild = child._belowSibling
                        if child._z < val or (child._z is val and isPreviousSibling(@, child))
                            if oldBelowSibling is child
                                break
                            @_belowSibling = child
                            aboveSibling = child._aboveSibling
                            if @_aboveSibling = child._aboveSibling
                                @_aboveSibling._belowSibling = @
                            child._aboveSibling = @
                            break
                        unless prevChild
                            @_belowSibling = null
                            @_aboveSibling = child
                            child._belowSibling = @

                # clean old siblings
                if oldBelowSibling and oldBelowSibling isnt @_belowSibling
                    oldBelowSibling._aboveSibling = oldAboveSibling
                if oldAboveSibling and oldAboveSibling isnt @_aboveSibling
                    oldAboveSibling._belowSibling = oldBelowSibling

                # new children
                if @_belowSibling
                    if children._bottomChild is @
                        children._bottomChild = oldAboveSibling
                else
                    children._bottomChild = @
                if @_aboveSibling
                    if children._topChild is @
                        children._topChild = oldBelowSibling
                else
                    children._topChild = @

                # implementation
                if oldAboveSibling isnt @_aboveSibling
                    insertItemInImpl @

                `//<development>`
                assert.isNot @_belowSibling, @
                assert.isNot @_belowSibling?._belowSibling, @
                assert.isNot @_aboveSibling, @
                assert.isNot @_aboveSibling?._aboveSibling, @
                if @_belowSibling
                    assert.is @_belowSibling._aboveSibling, @
                if @_aboveSibling
                    assert.is @_aboveSibling._belowSibling, @
                `//</development>`
                return

## *Float* Item::scale = `1`

## *Signal* Item::onScaleChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'scale'
            defaultValue: 1
            implementation: Impl.setItemScale
            developmentSetter: (val) ->
                assert.isFloat val, "Item.scale needs to be a float, but #{val} given"

## *Float* Item::rotation = `0`

```nml
Rectangle {
    width: 100
    height: 100
    color: 'red'
    rotation: Math.PI / 4
}
```

## *Signal* Item::onRotationChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'rotation'
            defaultValue: 0
            implementation: Impl.setItemRotation
            developmentSetter: (val) ->
                assert.isFloat val, "Item.rotation needs to be a float, but #{val} given"

## *Float* Item::opacity = `1`

## *Signal* Item::onOpacityChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'opacity'
            defaultValue: 1
            implementation: Impl.setItemOpacity
            developmentSetter: (val) ->
                assert.isFloat val, "Item.opacity needs to be a float, but #{val} given"

## *String* Item::linkUri = `''`

Points to the URI which will be used when user clicks on this item.

## *Signal* Item::onLinkUriChange(*String* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'linkUri'
            defaultValue: ''
            implementation: Impl.setItemLinkUri
            developmentSetter: (val) ->
                assert.isString val, "Item.linkUri needs to be a string, but #{val} given"

## Item::scaleInPoint(*Float* scale, *Float* pointX, *Float* pointY)

        scaleInPoint: (scale, pointX, pointY) ->
            oldScale = @scale

            # scale
            @scale *= scale

            # move to point horizontal
            {width} = @
            widthChange = (width * @scale - width * oldScale) / 2
            xOriginToChange = -2 * (pointX / width) + 1
            @x += xOriginToChange * widthChange

            # move to point vertical
            {height} = @
            heightChange = (height * @scale - height * oldScale) / 2
            yOriginToChange = -2 * (pointY / height) + 1
            @y += yOriginToChange * heightChange

            return

        @createSpacing = require('./item/spacing') Renderer, Impl, itemUtils, Item
        @createAlignment = require('./item/alignment') Renderer, Impl, itemUtils, Item
        @createAnchors = require('./item/anchors') Renderer, Impl, itemUtils, Item
        @createLayout = require('./item/layout') Renderer, Impl, itemUtils, Item
        @createMargin = require('./item/margin') Renderer, Impl, itemUtils, Item
        @createPointer = require('./item/pointer') Renderer, Impl, itemUtils, Item
        @createKeys = require('./item/keys') Renderer, Impl, itemUtils, Item

## *Item.Anchors* Item::anchors

## *Signal* Item::onAnchorsChange(*String* property, *Array* oldValue)

        @createAnchors @

## *Item.Layout* Item::layout

## *Signal* Item::onLayoutChange(*String* property, *Any* oldValue)

        @createLayout @

## *Item.Pointer* Item::pointer

        @Pointer = @createPointer @

## *Item.Margin* Item::margin

## *Signal* Item::onMarginChange(*String* property, *Any* oldValue)

        @createMargin @

## *Item.Keys* Item::keys

        @Keys = @createKeys @

        Item

# Item

    'use strict'

    assert = require 'src/assert'
    utils = require 'src/utils'
    signal = require 'src/signal'
    List = require 'src/list'

    {isArray} = Array
    {emitSignal} = signal.Emitter

    assert = assert.scope 'Renderer.Item'

    module.exports = (Renderer, Impl, itemUtils) -> class Item extends itemUtils.Object
        @__name__ = 'Item'
        @__path__ = 'Renderer.Item'

        Document = require 'src/document'
        DocElement = Document.Element

## *Item* Item.New([*Object* options])

        @New = (opts) ->
            item = new Item
            itemUtils.Object.initialize item, opts
            item

## *Item* Item::constructor()

This is a base class for everything which is visible.

        constructor: ->
            assert.instanceOf @, Item

            super()
            @_parent = null
            @_children = null
            @_previousSibling = null
            @_nextSibling = null
            @_belowSibling = null
            @_aboveSibling = null
            @_width = 0
            @_height = 0
            @_x = 0
            @_y = 0
            @_z = 0
            @_visible = true
            @_clip = false
            @_scale = 1
            @_rotation = 0
            @_opacity = 1
            @_linkUri = ''
            @_anchors = null
            @_layout = null
            @_keys = null
            @_pointer = null
            @_margin = null
            @_classes = null
            @_query = ''
            @_node = null

### Custom properties

```nml
Item {
    id: main
    property currentLife: 0.8
    Text {
        text: "Life: " + main.currentLife
    }
}
```

### Custom signals

```nml
Item {
    signal onPlayerCollision
    onPlayerCollision(){
        // boom!
    }
}
```

## ReadOnly *String* Item::query

        utils.defineProperty @::, 'query', null, ->
            @_query
        , (val) ->
            if @_query is ''
                @_query = val
            return

## ReadOnly *Document.Element* Item::node

## *Signal* Item::onNodeChange(*Document.Element* oldValue)

```javascript
Text {
    text: this.node.props.value
}
```

```javascript
Text {
    onNodeChange: function(){
        var inputs = this.node.queryAll('input[type=string]');
    }
}
```

        itemUtils.defineProperty
            constructor: @
            name: 'node'
            defaultValue: null
            developmentSetter: (val) ->
                if val?
                    assert.instanceOf val, DocElement

## *Signal* Item::ready()

Called when the Item is ready, that is, all
properties have been set and it's ready to use.

```nml
Rectangle {
    width: 200
    height: 50
    color: 'green'
    Rectangle {
        width: parent.width / 2
        height: parent.height / 2
        color: 'yellow'
        onReady: function(){
            console.log(this.width, this.height);
            // 100, 25
        }
    }
}
```

        signal.Emitter.createSignal @, 'onReady'

## *Signal* Item::onAnimationFrame(*Integer* miliseconds)

        signal.Emitter.createSignal @, 'onAnimationFrame', do ->
            now = Date.now()
            items = []

            frame = ->
                oldNow = now
                now = Date.now()
                ms = now - oldNow

                for item in items
                    emitSignal item, 'onAnimationFrame', ms
                requestAnimationFrame frame

            requestAnimationFrame? frame

            (item) ->
                items.push item

## ReadOnly *String* Item::id

## *Object* Item::children

        utils.defineProperty @::, 'children', null, ->
            @_children ||= new ChildrenObject(@)
        , (val) ->
            assert.isArray val, "Item.children needs to be an array, but #{val} given"
            @clear()
            for item in val
                val.parent = @
            return

## *Signal* Item::onChildrenChange(*Item* added, *Item* removed)

        signal.Emitter.createSignal @, 'onChildrenChange'

        class ChildrenObject extends itemUtils.MutableDeepObject
            constructor: (ref) ->
                @_layout = null
                @_target = null
                @_firstChild = null
                @_lastChild = null
                @_bottomChild = null
                @_topChild = null
                @_length = 0
                super ref

### ReadOnly *Item* Item::children.firstChild

            utils.defineProperty @::, 'firstChild', null, ->
                @_firstChild
            , null

### ReadOnly *Item* Item::children.lastChild

            utils.defineProperty @::, 'lastChild', null, ->
                @_lastChild
            , null

### ReadOnly *Item* Item::children.bottomChild

            utils.defineProperty @::, 'bottomChild', null, ->
                @_bottomChild
            , null

### ReadOnly *Item* Item::children.topChild

            utils.defineProperty @::, 'topChild', null, ->
                @_topChild
            , null

### ReadOnly *Integer* Item::children.length

            utils.defineProperty @::, 'length', null, ->
                @_length
            , null

### *Item* Item::children.layout

Item used to position children items.
Can be e.g. *Flow*, *Grid* etc.

### *Signal* Item::children.onLayoutChange(*Item* oldValue)

            itemUtils.defineProperty
                constructor: @
                name: 'layout'
                defaultValue: null
                developmentSetter: (val) ->
                    if val?
                        assert.instanceOf val, Item, """
                            Item.children.layout needs to be an Item, but #{val} given
                        """
                setter: (_super) -> (val) ->
                    if @_layout?.effectItem
                        @_layout.parent = null
                        @_layout.effectItem = @_layout

                    _super.call @, val

                    if '_effectItem' of @_ref
                        @_ref.effectItem = if val then null else @_ref

                    if val?
                        ref = @_ref
                        setFakeParent val, ref, 0
                        if val.effectItem
                            val.effectItem = ref

                    return

### *Item* Item::children.target

A new child trying to be added into the item with the `children.target` defined
will be added into the `target` item.

### *Signal* Item::children.onTargetChange(*Item* oldValue)

            itemUtils.defineProperty
                constructor: @
                name: 'target'
                defaultValue: null
                developmentSetter: (val) ->
                    if val?
                        assert.instanceOf val, Item, """
                            Item.children.target needs to be an Item, but #{val} given
                        """

### *Item* Item::children.get(*Integer* index)

Returns an item with the given index.

            get: (val) ->
                assert.operator val, '>=', 0, """
                    Item.children.get index cannot be lower than zero, #{val} given
                """
                assert.operator val, '<', @length, """
                    Item.children.get index must be lower than children.length, \
                    #{val} given
                """

                if val < @length / 2
                    sibling = @firstChild
                    while val > 0
                        sibling = sibling.nextSibling
                        val--
                else
                    sibling = @lastChild
                    while val > 0
                        sibling = sibling.previousSibling
                        val--

                sibling

### *Integer* Item::children.index(*Item* value)

Returns an index of the given child in the children array.

            index: (val) ->
                if @has(val)
                    val.index
                else
                    -1

### *Boolean* Item::children.has(*Item* value)

Returns `true` if the given item is an item child.

            has: (val) ->
                @_ref is val._parent

### Item::children.clear()

Removes all children from the item.

            clear: ->
                while last = @last
                    last.parent = null
                return

## *Item* Item::parent = `null`

## *Signal* Item::onParentChange(*Item* oldParent)

        setFakeParent = (child, parent, index=-1) ->
            child.parent = null

            if index >= 0 and parent.children._length < index
                Impl.insertItemBefore.call child, parent.children[index]
            else
                Impl.setItemParent.call child, parent

            child._parent = parent
            emitSignal child, 'onParentChange', null
            return

        updateZSiblingsForAppendedItem = (item, z, newChildren) ->
            child = newChildren._topChild
            while child
                if child._z <= z
                    if item._aboveSibling = child._aboveSibling
                        item._aboveSibling._belowSibling = item
                    item._belowSibling = child
                    child._aboveSibling = item
                    return
                unless nextChild = child._belowSibling
                    item._aboveSibling = child
                    child._belowSibling = item
                    item._belowSibling = null
                    return
                child = nextChild
            return

        insertItemInImpl = (item) ->
            if aboveSibling = item._aboveSibling
                Impl.insertItemBefore.call item, aboveSibling
            else
                Impl.setItemParent.call item, item._parent
            return

        itemUtils.defineProperty
            constructor: @
            name: 'parent'
            defaultValue: null
            setter: (_super) -> (val = null) ->
                old = @_parent
                oldChildren = old?.children
                valChildren = val?.children

                if valChildren?._target
                    # detect whether target is a child of this item
                    containsItem = false
                    tmpItem = valChildren._target
                    while tmpItem
                        if tmpItem is @
                            containsItem = true
                            break
                        tmpItem = tmpItem._parent

                    unless containsItem
                        val = valChildren._target
                        valChildren = val.children

                if old is val
                    return

                assert.isNot @, val, "Item.parent cannot be set with context item, #{val} given"

                if pointer = @_pointer
                    pointer.hover = pointer.pressed = false

                if val isnt null
                    assert.instanceOf val, Item, """
                        Item.parent needs to be an Item or null, but #{val} given
                    """

                # old siblings
                oldPreviousSibling = @_previousSibling
                oldNextSibling = @_nextSibling
                if oldPreviousSibling isnt null
                    oldPreviousSibling._nextSibling = oldNextSibling
                if oldNextSibling isnt null
                    oldNextSibling._previousSibling = oldPreviousSibling

                # new siblings
                if val isnt null
                    if previousSibling = @_previousSibling = valChildren.lastChild
                        previousSibling._nextSibling = @
                else
                    @_previousSibling = null
                if oldNextSibling isnt null
                    @_nextSibling = null

                # children
                if oldChildren
                    oldChildren._length -= 1
                    if oldChildren.firstChild is @
                        oldChildren._firstChild = oldNextSibling
                    if oldChildren.lastChild is @
                        oldChildren._lastChild = oldPreviousSibling
                if valChildren
                    if ++valChildren._length is 1
                        valChildren._firstChild = @
                    valChildren._lastChild = @

                # old z-index siblings
                oldBelowSibling = @_belowSibling
                oldAboveSibling = @_aboveSibling
                if oldBelowSibling isnt null
                    oldBelowSibling._aboveSibling = oldAboveSibling
                if oldAboveSibling isnt null
                    oldAboveSibling._belowSibling = oldBelowSibling

                # new z-index siblings
                @_belowSibling = @_aboveSibling = null
                if valChildren
                    updateZSiblingsForAppendedItem @, @_z, valChildren

                # z-index children
                if oldChildren
                    unless oldAboveSibling
                        oldChildren._topChild = oldBelowSibling
                    unless oldBelowSibling
                        oldChildren._bottomChild = oldAboveSibling
                if valChildren
                    unless @_aboveSibling
                        valChildren._topChild = @
                    unless @_belowSibling
                        valChildren._bottomChild = @

                # parent
                @_parent = val
                insertItemInImpl @

                `//<development>`
                assert.is @nextSibling, null
                if val
                    assert.is val.children.lastChild, @
                    assert.isDefined val.children.firstChild
                    assert.isDefined val.children.lastChild
                    assert.isDefined val.children.topChild
                    assert.isDefined val.children.bottomChild
                if old and old.children.length is 0
                    assert.isNotDefined old.children.firstChild
                    assert.isNotDefined old.children.lastChild
                    assert.isNotDefined old.children.topChild
                    assert.isNotDefined old.children.bottomChild
                `//</development>`

                # signals
                if old isnt null
                    emitSignal old, 'onChildrenChange', null, @
                if val isnt null
                    emitSignal val, 'onChildrenChange', @, null

                emitSignal @, 'onParentChange', old

                if oldPreviousSibling isnt null
                    emitSignal oldPreviousSibling, 'onNextSiblingChange', @
                if oldNextSibling isnt null
                    emitSignal oldNextSibling, 'onPreviousSiblingChange', @

                if val isnt null or oldPreviousSibling isnt null
                    if previousSibling
                        emitSignal previousSibling, 'onNextSiblingChange', null
                    emitSignal @, 'onPreviousSiblingChange', oldPreviousSibling
                if oldNextSibling isnt null
                    emitSignal @, 'onNextSiblingChange', oldNextSibling

                return

## *Item* Item::previousSibling

        utils.defineProperty @::, 'previousSibling', null, ->
            @_previousSibling
        , (val = null) ->
            assert.isNot @, val, """
                Item.previousSibling cannot be set with context Item, #{val} given
            """

            if val is @_previousSibling
                return

            if val
                assert.instanceOf val, Item, """
                    Item.previousSibling must be an Item or null, but #{val} given
                """
                nextSibling = val._nextSibling
                if not nextSibling and val._parent isnt @_parent
                    @parent = val._parent
                else
                    @nextSibling = nextSibling
            else
                assert.isDefined @_parent, """
                    Cannot null Item.previousSibling when Item has no parent
                """
                @nextSibling = @_parent.children.firstChild

            assert.is @_previousSibling, val
            return

## *Signal* Item::onPreviousSiblingChange(*Item* oldValue)

        signal.Emitter.createSignal @, 'onPreviousSiblingChange'

## *Item* Item::nextSibling

        isNextSibling = (item, sibling) ->
            while item
                nextItem = item._nextSibling
                if nextItem is sibling
                    return true
                item = nextItem
            return false

        isPreviousSibling = (item, sibling) ->
            while item
                prevItem = item._previousSibling
                if prevItem is sibling
                    return true
                item = prevItem
            return false

        updateZSiblingsForInsertedItem = (item, nextSibling, z, newChildren) ->
            if nextSibling._z is z
                # simple case - the same z-index as in nextSibling
                if item._belowSibling = nextSibling._belowSibling
                    item._belowSibling._aboveSibling = item
                item._aboveSibling = nextSibling
                nextSibling._belowSibling = item
            else
                # hard case - different z-indexes
                nextChild = newChildren._bottomChild
                while child = nextChild
                    nextChild = child._aboveSibling
                    if child._z > z or (child._z is z and isNextSibling(item, child))
                        item._aboveSibling = child
                        if item._belowSibling = child._belowSibling
                            item._belowSibling._aboveSibling = item
                        child._belowSibling = item
                        break
                    unless nextChild
                        item._aboveSibling = null
                        item._belowSibling = child
                        child._aboveSibling = item
            return

        utils.defineProperty @::, 'nextSibling', null, ->
            @_nextSibling
        , (val = null) ->
            assert.isNot @, val, """
                Item.nextSibling cannot be set with context Item, #{val} given
            """
            if val
                assert.instanceOf val, Item, """
                    Item.nextSibling needs to be an Item or null, but #{val} given
                """
                assert.isDefined val._parent, """
                    Item.nextSibling value needs to have a parent, given #{val} has no parent
                """
            else
                assert.isDefined @_parent, """
                    Cannot null Item.nextSibling when Item has no parent
                """

            if val is @_nextSibling
                return

            oldParent = @_parent
            oldChildren = oldParent?._children
            oldPreviousSibling = @_previousSibling
            oldNextSibling = @_nextSibling

            if val
                newParent = val._parent
                newChildren = newParent._children
            else
                newParent = oldParent
                newChildren = oldChildren

            # new parent
            @_parent = newParent

            # current siblings
            oldPreviousSibling?._nextSibling = oldNextSibling
            oldNextSibling?._previousSibling = oldPreviousSibling

            # new siblings
            previousSibling = previousSiblingOldNextSibling = null
            nextSibling = nextSiblingOldPreviousSibling = null
            if val
                if previousSibling = val._previousSibling
                    previousSiblingOldNextSibling = previousSibling._nextSibling
                    previousSibling._nextSibling = @

                nextSibling = val
                nextSiblingOldPreviousSibling = nextSibling._previousSibling
                nextSibling._previousSibling = @
            else
                if previousSibling = newChildren.lastChild
                    previousSibling._nextSibling = @

            @_previousSibling = previousSibling
            @_nextSibling = nextSibling

            # children
            if oldChildren
                oldChildren._length -= 1
                unless oldPreviousSibling
                    oldChildren._firstChild = oldNextSibling
                unless oldNextSibling
                    oldChildren._lastChild = oldPreviousSibling
            newChildren._length += 1
            if newChildren.firstChild is val
                newChildren._firstChild = @
            unless val
                newChildren._lastChild = @

            # old z-index siblings
            oldBelowSibling = @_belowSibling
            oldAboveSibling = @_aboveSibling
            if oldBelowSibling isnt null
                oldBelowSibling._aboveSibling = oldAboveSibling
            if oldAboveSibling isnt null
                oldAboveSibling._belowSibling = oldBelowSibling

            # new z-index siblings
            @_belowSibling = @_aboveSibling = null
            if nextSibling
                updateZSiblingsForInsertedItem @, nextSibling, @_z, newChildren
            else
                updateZSiblingsForAppendedItem @, @_z, newChildren

            # z-index children
            if oldChildren
                unless oldAboveSibling
                    oldChildren._topChild = oldBelowSibling
                unless oldBelowSibling
                    oldChildren._bottomChild = oldAboveSibling
            unless @_aboveSibling
                newChildren._topChild = @
            unless @_belowSibling
                newChildren._bottomChild = @

            # implementation
            insertItemInImpl @

            `//<development>`
            assert.is @_nextSibling, val
            assert.is @_parent, newParent
            if val
                assert.is @_parent, val._parent
            if @_previousSibling
                assert.is @_previousSibling._nextSibling, @
            if @_nextSibling
                assert.is @_nextSibling._previousSibling, @
            if oldPreviousSibling
                assert.is oldPreviousSibling._nextSibling, oldNextSibling
            if oldNextSibling
                assert.is oldNextSibling._previousSibling, oldPreviousSibling
            `//</development>`

            # children signal
            if oldParent isnt newParent
                if oldParent
                    emitSignal oldParent, 'onChildrenChange', null, @
                emitSignal newParent, 'onChildrenChange', @, null
                emitSignal @, 'onParentChange', oldParent
            else
                emitSignal newParent, 'onChildrenChange', null, null

            # current siblings signals
            if oldPreviousSibling
                emitSignal oldPreviousSibling, 'onNextSiblingChange', @
            if oldNextSibling
                emitSignal oldNextSibling, 'onPreviousSiblingChange', @

            # new siblings signals
            emitSignal @, 'onPreviousSiblingChange', oldPreviousSibling
            if previousSibling
                emitSignal previousSibling, 'onNextSiblingChange', previousSiblingOldNextSibling
            emitSignal @, 'onNextSiblingChange', oldNextSibling
            if nextSibling
                emitSignal nextSibling, 'onPreviousSiblingChange', nextSiblingOldPreviousSibling

            return

## *Signal* Item::onNextSiblingChange(*Item* oldValue)

        signal.Emitter.createSignal @, 'onNextSiblingChange'

## ReadOnly *Item* Item::belowSibling

        utils.defineProperty @::, 'belowSibling', null, ->
            @_belowSibling
        , null

## ReadOnly *Item* Item::aboveSibling

        utils.defineProperty @::, 'aboveSibling', null, ->
            @_aboveSibling
        , null

## *Integer* Item::index

        utils.defineProperty @::, 'index', null, ->
            index = 0
            sibling = @
            while sibling = sibling.previousSibling
                index++
            index
        , (val) ->
            assert.isInteger val, "Item.index needs to be a integer, but #{val} given"
            assert.isDefined @_parent, """
                When setting Item.index, item needs to have a parent, #{@} has no parent
            """
            assert.operator val, '>=', 0, "Item.index needs to greater than zero, #{val} given"
            assert.operator val, '<=', @_parent._children.length, """
                Item.index needs to be lower than parent.children.length, #{val} given
            """

            {children} = @parent
            if val >= children.length
                @nextSibling = null
            else if (valItem = children.get(val)) isnt @
                @nextSibling = valItem

            return

## *Boolean* Item::visible = `true`

Determines whether an item is visible or not.

```nml
Item {
    width: 100
    height: 100
    pointer.onClick: function(){
        rect.visible = !rect.visible;
        text.text = rect.visible ? "Click to hide" : "Click to show";
    }
    Rectangle {
        id: rect
        anchors.fill: parent
        color: 'blue'
    }
    Text {
        id: text
        text: "Click to hide"
        anchors.centerIn: parent
    }
}
```

## *Signal* Item::onVisibleChange(*Boolean* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'visible'
            defaultValue: true
            implementation: Impl.setItemVisible
            developmentSetter: (val) ->
                assert.isBoolean val, "Item.visible needs to be a boolean, but #{val} given"

## *Boolean* Item::clip = `false`

## *Signal* Item::onClipChange(*Boolean* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'clip'
            defaultValue: false
            implementation: Impl.setItemClip
            developmentSetter: (val) ->
                assert.isBoolean val, "Item.clip needs to be a boolean, but #{val} given"

## *Float* Item::width = `0`

## *Signal* Item::onWidthChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'width'
            defaultValue: 0
            implementation: Impl.setItemWidth
            developmentSetter: (val) ->
                assert.isFloat val, "Item.width needs to be a float, but #{val} given"

## *Float* Item::height = `0`

## *Signal* Item::onHeightChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'height'
            defaultValue: 0
            implementation: Impl.setItemHeight
            developmentSetter: (val) ->
                assert.isFloat val, "Item.height needs to be a float, but #{val} given"

## *Float* Item::x = `0`

## *Signal* Item::onXChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'x'
            defaultValue: 0
            implementation: Impl.setItemX
            developmentSetter: (val) ->
                assert.isFloat val, "Item.x needs to be a float, but #{val} given"

## *Float* Item::y = `0`

## *Signal* Item::onYChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'y'
            defaultValue: 0
            implementation: Impl.setItemY
            developmentSetter: (val) ->
                assert.isFloat val, "Item.y needs to be a float, but #{val} given"

## *Float* Item::z = `0`

## *Signal* Item::onZChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'z'
            defaultValue: 0
            developmentSetter: (val) ->
                assert.isFloat val, "Item.z needs to be a float, but #{val} given"
            setter: (_super) -> (val) ->
                oldVal = @_z
                if oldVal is val
                    return

                _super.call @, val

                unless parent = @_parent
                    return
                children = parent._children
                oldAboveSibling = @_aboveSibling
                oldBelowSibling = @_belowSibling

                # new siblings
                if val > oldVal
                    nextChild = @_aboveSibling
                    while child = nextChild
                        nextChild = child._aboveSibling
                        if child._z > val or (child._z is val and isNextSibling(@, child))
                            if oldAboveSibling is child
                                break
                            @_aboveSibling = child
                            if @_belowSibling = child._belowSibling
                                @_belowSibling._aboveSibling = @
                            child._belowSibling = @
                            break
                        unless nextChild
                            @_aboveSibling = null
                            @_belowSibling = child
                            child._aboveSibling = @

                if val < oldVal
                    prevChild = @_belowSibling
                    while child = prevChild
                        prevChild = child._belowSibling
                        if child._z < val or (child._z is val and isPreviousSibling(@, child))
                            if oldBelowSibling is child
                                break
                            @_belowSibling = child
                            aboveSibling = child._aboveSibling
                            if @_aboveSibling = child._aboveSibling
                                @_aboveSibling._belowSibling = @
                            child._aboveSibling = @
                            break
                        unless prevChild
                            @_belowSibling = null
                            @_aboveSibling = child
                            child._belowSibling = @

                # clean old siblings
                if oldBelowSibling and oldBelowSibling isnt @_belowSibling
                    oldBelowSibling._aboveSibling = oldAboveSibling
                if oldAboveSibling and oldAboveSibling isnt @_aboveSibling
                    oldAboveSibling._belowSibling = oldBelowSibling

                # new children
                if @_belowSibling
                    if children._bottomChild is @
                        children._bottomChild = oldAboveSibling
                else
                    children._bottomChild = @
                if @_aboveSibling
                    if children._topChild is @
                        children._topChild = oldBelowSibling
                else
                    children._topChild = @

                # implementation
                if oldAboveSibling isnt @_aboveSibling
                    insertItemInImpl @

                `//<development>`
                assert.isNot @_belowSibling, @
                assert.isNot @_belowSibling?._belowSibling, @
                assert.isNot @_aboveSibling, @
                assert.isNot @_aboveSibling?._aboveSibling, @
                if @_belowSibling
                    assert.is @_belowSibling._aboveSibling, @
                if @_aboveSibling
                    assert.is @_aboveSibling._belowSibling, @
                `//</development>`
                return

## *Float* Item::scale = `1`

## *Signal* Item::onScaleChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'scale'
            defaultValue: 1
            implementation: Impl.setItemScale
            developmentSetter: (val) ->
                assert.isFloat val, "Item.scale needs to be a float, but #{val} given"

## *Float* Item::rotation = `0`

```nml
Rectangle {
    width: 100
    height: 100
    color: 'red'
    rotation: Math.PI / 4
}
```

## *Signal* Item::onRotationChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'rotation'
            defaultValue: 0
            implementation: Impl.setItemRotation
            developmentSetter: (val) ->
                assert.isFloat val, "Item.rotation needs to be a float, but #{val} given"

## *Float* Item::opacity = `1`

## *Signal* Item::onOpacityChange(*Float* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'opacity'
            defaultValue: 1
            implementation: Impl.setItemOpacity
            developmentSetter: (val) ->
                assert.isFloat val, "Item.opacity needs to be a float, but #{val} given"

## *String* Item::linkUri = `''`

Points to the URI which will be used when user clicks on this item.

## *Signal* Item::onLinkUriChange(*String* oldValue)

        itemUtils.defineProperty
            constructor: @
            name: 'linkUri'
            defaultValue: ''
            implementation: Impl.setItemLinkUri
            developmentSetter: (val) ->
                assert.isString val, "Item.linkUri needs to be a string, but #{val} given"

        @createSpacing = require('./item/spacing') Renderer, Impl, itemUtils, Item
        @createAlignment = require('./item/alignment') Renderer, Impl, itemUtils, Item
        @createAnchors = require('./item/anchors') Renderer, Impl, itemUtils, Item
        @createLayout = require('./item/layout') Renderer, Impl, itemUtils, Item
        @createMargin = require('./item/margin') Renderer, Impl, itemUtils, Item
        @createPointer = require('./item/pointer') Renderer, Impl, itemUtils, Item
        @createKeys = require('./item/keys') Renderer, Impl, itemUtils, Item

## *Item.Anchors* Item::anchors

## *Signal* Item::onAnchorsChange(*String* property, *Array* oldValue)

        @createAnchors @

## *Item.Layout* Item::layout

## *Signal* Item::onLayoutChange(*String* property, *Any* oldValue)

        @createLayout @

## *Item.Pointer* Item::pointer

        @Pointer = @createPointer @

## *Item.Margin* Item::margin

## *Signal* Item::onMarginChange(*String* property, *Any* oldValue)

        @createMargin @

## *Item.Keys* Item::keys

        @Keys = @createKeys @

        Item


Add rpc.on, which proxies to socket.on

Add rpc.on, which proxies to socket.on

# RPC

Define an Angular service to issue
[remote procedure calls](http://en.wikipedia.org/wiki/Remote_procedure_call#Message_passing).

    exports.pkgmanRegister = (registrar) ->

#### Implements hook `shrubAngularService`.

      registrar.registerHook 'shrubAngularService', -> [
        '$injector', '$q', 'shrub-pkgman', 'shrub-socket'
        ({invoke}, {defer}, pkgman, socket) ->

          errors = require 'errors'

          service = {}

## rpc.call

* (String) `path` - The RPC route path, e.g. `shrub-user/login`.
* (Object) `data` - The data to send to the server.

*Call the server with some data.*

Returns a promise, either resolved with the result of the response
from the server, or rejected with the error from the server.

          service.call = (path, data) ->

            deferred = defer()

            socket.emit(
              'shrub-rpc'
              path: path, data: data
              ({error, result}) ->
                return deferred.reject errors.unserialize error if error?
                deferred.resolve result
            )

#### Invoke hook `shrubRpcCall`.

            invoke(
              injectable, null

              route: path
              data: data
              result: deferred.promise

            ) for injectable in pkgman.invokeFlat 'shrubRpcCall'

            deferred.promise

## rpc.on

* (String) `eventName` - The name of the event to listen for.
* (optional Function) `fn` - Callback called with the event data.

*Listen for an event.*

Proxies directly to `socket.on`.

          service.on = (eventName, fn) -> socket.on eventName, fn

## rpc.formSubmitHandler

* (String) `path` - The RPC route path, e.g. `shrub-user/login`.
* (Function) `fn` - Nodeback called with the RPC response.

*Helper function to call an RPC route with the result of a form submission.*

          service.formSubmitHandler = (path, fn) ->

            unless fn?
              fn = path
              path = null

            (values, form) ->

              service.call(path ? form.key, values).then(
                (result) -> fn null, result
              ).catch (error) -> fn error

          service

      ]

# RPC

Define an Angular service to issue
[remote procedure calls](http://en.wikipedia.org/wiki/Remote_procedure_call#Message_passing).

    exports.pkgmanRegister = (registrar) ->

#### Implements hook `shrubAngularService`.

      registrar.registerHook 'shrubAngularService', -> [
        '$injector', '$q', 'shrub-pkgman', 'shrub-socket'
        ({invoke}, {defer}, pkgman, socket) ->

          errors = require 'errors'

          service = {}

## rpc.call

* (String) `path` - The RPC route path, e.g. `shrub-user/login`.
* (Object) `data` - The data to send to the server.

*Call the server with some data.*

Returns a promise, either resolved with the result of the response
from the server, or rejected with the error from the server.

          service.call = (path, data) ->

            deferred = defer()

            socket.emit(
              'shrub-rpc'
              path: path, data: data
              ({error, result}) ->
                return deferred.reject errors.unserialize error if error?
                deferred.resolve result
            )

#### Invoke hook `shrubRpcCall`.

            invoke(
              injectable, null

              route: path
              data: data
              result: deferred.promise

            ) for injectable in pkgman.invokeFlat 'shrubRpcCall'

            deferred.promise

## rpc.formSubmitHandler

* (String) `path` - The RPC route path, e.g. `shrub-user/login`.
* (Function) `fn` - Nodeback called with the RPC response.

*Helper function to call an RPC route with the result of a form submission.*

          service.formSubmitHandler = (path, fn) ->

            unless fn?
              fn = path
              path = null

            (values, form) ->

              service.call(path ? form.key, values).then(
                (result) -> fn null, result
              ).catch (error) -> fn error

          service

      ]


ascii art

ascii art

    fs = require 'fs'
    path = require 'path'
    handlebars = require 'handlebars'
    aws = require 'aws-sdk'
    shortid = require 'shortid'
    Hashids = require 'hashids'
    hashids = new Hashids(process.env["AWS_ACCESS_KEY"])

Grab our environment variables...

    DOMAIN = process.env["DOMAIN"] || "thelee.ch"
    BUCKET = process.env["BUCKET"] || DOMAIN
    GA_ID = process.env["GA_ID"]
    PARTITION = process.env["PARTITION"] || false

Setup the connection to s3

    aws.config.update {
        accessKeyId: process.env["AWS_ACCESS_KEY"],
        secretAccessKey: process.env["AWS_SECRET_KEY"]
    }
    aws.config.region = 'us-east-1'
    s3 = new aws.S3()

Make sure the S3 bucket is setup as a website. We'll just do this each time we
start the app. This means that it will frequently fail, but it's the simplest
way to make sure that we've setup the bucket correctly.

    s3.createBucket { Bucket: DOMAIN, ACL: "public-read" }, (err, data) ->
      if err
        console.log "[ERROR]: #{err}"
      else
        welcome = fs.readFileSync path.join(__dirname, "welcome-ascii.txt")
        welcome = "<pre>#{welcome}</pre>"
        params = {
          Bucket: BUCKET
          Key: "index.html",
          ACL: "public-read",
          Body: welcome,
          ContentType: "text/html"
        }
        s3.putObject params, (err, data) ->
          if err
            console.log "[ERROR]: error creating index.html #{err}"
            return
          params = {
            Bucket: BUCKET,
            WebsiteConfiguration: {
              IndexDocument: {
                Suffix: 'index.html'
              }
            }
          }
          s3.putBucketWebsite params, (err, data) ->
            if err
              console.log "[ERROR]: #{err}"

--------
We're going to make `leech` (this module) exportable so that we can use it in
the app, as a command line tool, and as it's own funciton. It takes 1 argument
(the url) which makes it easy to plug-n-play in other stuff.

    module.exports = (url, fn) ->

This is our basic HTML template that we'll use for doing the redirect. It's just
going to send the user to another page as soon as it's loaded. There's no server
since it's just a static file, but everything will be tracked by GA.

      source = """
      <html>
          <title>{{url}}</title>
          <body>
          <script>
            <!-- Google Analytics -->
              (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
              (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
              m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
              })(window,document,'script','//www.google-analytics.com/analytics.js','ga');

              ga('create', '{{ga_id}}', 'auto');
              ga('send', 'pageview');
              // redirect
              window.location.replace('{{url}}');
            </script>
          </body>
      </html>
      """

      template = handlebars.compile(source)

Data should just be the user's Google Analytics Id and the URL that they want to
minify.

      data = { url: url, ga_id: GA_ID }
      html = template(data)

We're going to generate a shortlink for the URL. [`shortid`](https://github.com/dylang/shortid)
does a pretty good job at balancing between being short, and also being unique!
We'll take that `_id` and turn it into the key for an S3 object. If you want
this to be really "scalable", you can "hash" your S3 keys. All this means is
that you split the key into 2 parts like so: ("abcd123" --> "abc/d123"). S3 will
automatically partition you keys across more servers and will dramatically
increase preformance.

      shortid.characters "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ()"
      _id = shortid.generate()
      if PARTITION
        _id = _id.slice(0, 3) + "/" + _id.slice(3)
      params = {
        Bucket: BUCKET,
        Key: _id
        ACL: "public-read",
        Body: html,
        ContentType: "text/html",
        Metadata: {
          url: url
        }
      }
      s3.putObject params, (err, data) ->
          if err
            console.log err
          fn err, path.join(DOMAIN, _id)

    path = require 'path'
    handlebars = require 'handlebars'
    aws = require 'aws-sdk'
    shortid = require 'shortid'
    Hashids = require 'hashids'
    hashids = new Hashids(process.env["AWS_ACCESS_KEY"])

Grab our environment variables...

    DOMAIN = process.env["DOMAIN"] || "thelee.ch"
    BUCKET = process.env["BUCKET"] || DOMAIN
    GA_ID = process.env["GA_ID"]
    PARTITION = process.env["PARTITION"] || false

Setup the connection to s3

    aws.config.update {
        accessKeyId: process.env["AWS_ACCESS_KEY"],
        secretAccessKey: process.env["AWS_SECRET_KEY"]
    }
    aws.config.region = 'us-east-1'
    s3 = new aws.S3()

Make sure the S3 bucket is setup as a website. We'll just do this each time we
start the app. This means that it will frequently fail, but it's the simplest
way to make sure that we've setup the bucket correctly.

    s3.createBucket { Bucket: DOMAIN }, (err, data) ->
      if err
        console.log "[ERROR]: #{err}"
      else
        console.log "Bucket was created for your domain. URL is #{data.url}"
        welcome = fs.readFileSync path.join(__dirname, "welcome-leech.txt")
        params = {
          Bucket: BUCKET,
          Key: "index.html",
          ACL: "public-read",
          Body: welcome,
          ContentType: "text/html"
        }
        s3.putObject params, (err, data) ->
            if err
              console.log "[ERROR]: #{err}"

--------
We're going to make `leech` (this module) exportable so that we can use it in
the app, as a command line tool, and as it's own funciton. It takes 1 argument
(the url) which makes it easy to plug-n-play in other stuff.

    module.exports = (url, fn) ->

This is our basic HTML template that we'll use for doing the redirect. It's just
going to send the user to another page as soon as it's loaded. There's no server
since it's just a static file, but everything will be tracked by GA.

      source = """
      <html>
          <title>{{url}}</title>
          <body>
          <script>
            <!-- Google Analytics -->
              (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
              (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
              m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
              })(window,document,'script','//www.google-analytics.com/analytics.js','ga');

              ga('create', '{{ga_id}}', 'auto');
              ga('send', 'pageview');
              // redirect
              window.location.replace('{{url}}');
            </script>
          </body>
      </html>
      """

      template = handlebars.compile(source)

Data should just be the user's Google Analytics Id and the URL that they want to
minify.

      data = { url: url, ga_id: GA_ID }
      html = template(data)

We're going to generate a shortlink for the URL. [`shortid`](https://github.com/dylang/shortid)
does a pretty good job at balancing between being short, and also being unique!
We'll take that `_id` and turn it into the key for an S3 object. If you want
this to be really "scalable", you can "hash" your S3 keys. All this means is
that you split the key into 2 parts like so: ("abcd123" --> "abc/d123"). S3 will
automatically partition you keys across more servers and will dramatically
increase preformance.

      shortid.characters "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ()"
      _id = shortid.generate()
      if PARTITION
        _id = _id.slice(0, 3) + "/" + _id.slice(3)
      params = {
        Bucket: BUCKET,
        Key: _id
        ACL: "public-read",
        Body: html,
        ContentType: "text/html",
        Metadata: {
          url: url
        }
      }
      s3.putObject params, (err, data) ->
          if err
            console.log err
          fn err, path.join(DOMAIN, _id)


Proper array/object Promise.all differentiation, with correct error handling semantics

# Angular

*Coordinate various core functionality.*

    _ = require 'lodash'
    Promise = require 'bluebird'

    config = require 'config'

    exports.pkgmanRegister = (registrar) ->

#### Implements hook `shrubAngularAHrefSanitizationWhitelist`.

      registrar.registerHook 'shrubAngularAHrefSanitizationWhitelist', -> [

Allow more protocols.

        '(?:https?|ftp|mailto|tel|file):'

Allow javascript:void(0).

        'javascript:void\\(0\\)'
      ]

#### Implements hook `shrubAngularAppConfig`.

      registrar.registerHook 'shrubAngularAppConfig', -> [
        '$compileProvider', '$injector', '$provide', '$routeProvider', '$locationProvider', 'shrub-pkgmanProvider'
        ($compileProvider, $injector, $provide, $routeProvider, $locationProvider, pkgmanProvider) ->

#### Invoke hook `shrubAngularAHrefSanitizationWhitelist`.

          regexes = []
          for regexes_ in pkgmanProvider.invokeFlat(
            'shrubAngularAHrefSanitizationWhitelist'
          )
            regexes.push regex for regex in regexes_

          $compileProvider.aHrefSanitizationWhitelist new RegExp(
            "^\s*(?:#{regexes.join '|'})"
          )

          unless config.get 'packageConfig:shrub-core:testMode'
            $compileProvider.debugInfoEnabled false

Completely override $q with Bluebird, because it's awesome.

###### TODO: Angular also implements a private service called $$q used for animation. We should override that one, too.

          $provide.decorator '$q', [
            '$rootScope', '$exceptionHandler'
            ($rootScope, $exceptionHandler) ->

              Promise.onPossiblyUnhandledRejection (error) ->

$timeout and $interval will throw this for cancellation. It's non-notable.

                return if 'canceled' is error.message

                $exceptionHandler error

Hook Bluebird's schedule up to Angular.

              Promise.setScheduler (fn) -> $rootScope.$evalAsync fn

## Promise.defer

See: https://docs.angularjs.org/api/ng/service/$q#the-deferred-api

              Promise.defer = ->
                resolve = null
                reject = null

                promise = new Promise ->
                  resolve = arguments[0]
                  reject = arguments[1]

Angular depends on notify, which is a crap API. We'll hack support for it in.

                __notifications = []
                proxyThen = promise.then
                promise.then = ->
                  args = (arg for arg in arguments)
                  __notifications.push args[2] if args[2]?
                  proxyThen.apply promise, args
                notify: (args...) -> fn args... for fn in __notifications

                promise: promise
                resolve: resolve
                reject: reject

## Promise.when

See: https://docs.angularjs.org/api/ng/service/$q#when

              Promise.when = (value, handlers...) ->
                Promise.cast(value).then handlers...

Proxy Promise.all because Angular supports passing in an object where the
values are promises, and the result is an object keyed with the resolved
values from the promise.

              originalAll = Promise.all
              Promise.all = (promises) ->

Cast it to a promise to be able to determine whether it's an array.

                Promise.cast(promises).then ->

Defer to Bluebird if it's an array.

                  return originalAll promises if angular.isArray promises

If it's not an object, defer to Bluebird (it'll throw).

                  return originalAll promises unless angular.isObject promises

Track the keys so we can map the values.

                  promiseKeys = []
                  promiseArray = for key, promise of promises
                    promiseKeys.push key
                    promise

                  originalAll(promiseArray).then (results) ->
                    objectResult = {}

                    for result, index in results
                      objectResult[promiseKeys[index]] = result

                    objectResult

              Promise

          ]

#### Invoke hook `shrubAngularRoutes`.

Allow packages to define routes in the Angular application.

          routes = {}
          for route in _.flatten pkgmanProvider.invokeFlat 'shrubAngularRoutes'
            routes[route.path ? path] = route

Invoke hook `shrubAngularRoutesAlter`.

Allow packages to alter defined routes.

          $injector.invoke(
            injectable, null
            routes: routes
          ) for injectable in pkgmanProvider.invokeFlat 'shrubAngularRoutesAlter'

          for path, route of routes
            do (path, route) ->

Wrap the controller so we can provide some automatic behavior.

              routeController = route.controller
              route.controller = [
                '$controller', '$injector', '$q', '$scope'
                ($controller, $injector, $q, $scope) ->

                  unless routeController?
                    return $scope.$emit 'shrub.core.routeRendered'

Controllers may return a promise, so wait until any returned value fulfills.
If it's not a promise, this will be in the next tick.

                  $q.when($injector.invoke(
                    routeController, null
                    $scope: $scope
                    route: route
                  )).then(-> $scope.$emit 'shrub.core.routeRendered').done()

              ]

              route.template ?= ' '

Register the path into Angular.

              $routeProvider.when "/#{route.path ? path}", route

Create a unique entry point.

          $routeProvider.when '/shrub-angular-entry-point', {}

Turn on HTML5 mode: "Real" URLs.

          $locationProvider.html5Mode true
      ]

# Angular

*Coordinate various core functionality.*

    _ = require 'lodash'
    Promise = require 'bluebird'

    config = require 'config'

    exports.pkgmanRegister = (registrar) ->

#### Implements hook `shrubAngularAHrefSanitizationWhitelist`.

      registrar.registerHook 'shrubAngularAHrefSanitizationWhitelist', -> [

Allow more protocols.

        '(?:https?|ftp|mailto|tel|file):'

Allow javascript:void(0).

        'javascript:void\\(0\\)'
      ]

#### Implements hook `shrubAngularAppConfig`.

      registrar.registerHook 'shrubAngularAppConfig', -> [
        '$compileProvider', '$injector', '$provide', '$routeProvider', '$locationProvider', 'shrub-pkgmanProvider'
        ($compileProvider, $injector, $provide, $routeProvider, $locationProvider, pkgmanProvider) ->

#### Invoke hook `shrubAngularAHrefSanitizationWhitelist`.

          regexes = []
          for regexes_ in pkgmanProvider.invokeFlat(
            'shrubAngularAHrefSanitizationWhitelist'
          )
            regexes.push regex for regex in regexes_

          $compileProvider.aHrefSanitizationWhitelist new RegExp(
            "^\s*(?:#{regexes.join '|'})"
          )

          unless config.get 'packageConfig:shrub-core:testMode'
            $compileProvider.debugInfoEnabled false

Completely override $q with Bluebird, because it's awesome.

###### TODO: Angular also implements a private service called $$q used for animation. We should override that one, too.

          $provide.decorator '$q', [
            '$rootScope', '$exceptionHandler'
            ($rootScope, $exceptionHandler) ->

              Promise.onPossiblyUnhandledRejection (error) ->

$timeout and $interval will throw this for cancellation. It's non-notable.

                return if 'canceled' is error.message

                $exceptionHandler error

Hook Bluebird's schedule up to Angular.

              Promise.setScheduler (fn) -> $rootScope.$evalAsync fn

## Promise.defer

See: https://docs.angularjs.org/api/ng/service/$q#the-deferred-api

              Promise.defer = ->
                resolve = null
                reject = null

                promise = new Promise ->
                  resolve = arguments[0]
                  reject = arguments[1]

Angular depends on notify, which is a crap API. We'll hack support for it in.

                __notifications = []
                proxyThen = promise.then
                promise.then = ->
                  args = (arg for arg in arguments)
                  __notifications.push args[2] if args[2]?
                  proxyThen.apply promise, args
                notify: (args...) -> fn args... for fn in __notifications

                promise: promise
                resolve: resolve
                reject: reject

## Promise.when

See: https://docs.angularjs.org/api/ng/service/$q#when

              Promise.when = (value, handlers...) ->
                Promise.cast(value).then handlers...

Proxy Promise.all because Angular supports passing in an object where the
values are promises, and the result is an object keyed with the resolved
values from the promise.

              originalAll = Promise.all
              Promise.all = (promises) ->

Defer to Bluebird unless it's an object.

                return originalAll promises unless angular.isObject(
                  promises
                )

Track the keys so we can map the values.

                promiseKeys = []
                promiseArray = for key, promise of promises
                  promiseKeys.push key
                  promise

                originalAll(promiseArray).then (results) ->
                  objectResult = {}

                  for result, index in results
                    objectResult[promiseKeys[index]] = result

                  objectResult

              Promise

          ]

#### Invoke hook `shrubAngularRoutes`.

Allow packages to define routes in the Angular application.

          routes = {}
          for route in _.flatten pkgmanProvider.invokeFlat 'shrubAngularRoutes'
            routes[route.path ? path] = route

Invoke hook `shrubAngularRoutesAlter`.

Allow packages to alter defined routes.

          $injector.invoke(
            injectable, null
            routes: routes
          ) for injectable in pkgmanProvider.invokeFlat 'shrubAngularRoutesAlter'

          for path, route of routes
            do (path, route) ->

Wrap the controller so we can provide some automatic behavior.

              routeController = route.controller
              route.controller = [
                '$controller', '$injector', '$q', '$scope'
                ($controller, $injector, $q, $scope) ->

                  unless routeController?
                    return $scope.$emit 'shrub.core.routeRendered'

Controllers may return a promise, so wait until any returned value fulfills.
If it's not a promise, this will be in the next tick.

                  $q.when($injector.invoke(
                    routeController, null
                    $scope: $scope
                    route: route
                  )).then(-> $scope.$emit 'shrub.core.routeRendered').done()

              ]

              route.template ?= ' '

Register the path into Angular.

              $routeProvider.when "/#{route.path ? path}", route

Create a unique entry point.

          $routeProvider.when '/shrub-angular-entry-point', {}

Turn on HTML5 mode: "Real" URLs.

          $locationProvider.html5Mode true
      ]


ancestor tests pass on component

ancestor tests pass on component

# CLASS: Component
* Extends: [Shape][Shape]
* Parent: [Index][Parent]

An interactive component

---

    Event = require 'ecl/dist/event'
    module.exports = class Component extends require './shape'

## CONSTRUCTOR
### new Component()
* Returns: [Component][Component]

Creates Component instance.

      constructor: ->
        super

Register validating listeners for each **type** from the list.

        for type in ['grab', 'release', 'drag']

Localize the **type** variable.

          do (type) =>

Add capturing listener which will cancel and stop the event
if the event type is not enabled.

            @addListener type:type, capture:yes, listener: (event) ->
              event.cancel().stop() unless @events?[type]

Add normal listener which will cancel and stop the event
if the event type is not enabled.

            @addListener type:type, capture:no, listener: (event) ->
              event.cancel().stop() unless @events?[type]

Register extendable listeners for each **type** from the list.

        for type in ['grab', 'release', 'drag']

Add capturing extendable listener

          @addListener type, this["#{type}CaptureListener"], yes

Add normal extendable listener

          @addListener type, this["#{type}Listener"], no

#### PARAMETERS
* **args** - named arguments

---

## PROPERTIES

---

## METHODS
### #mousemoveCaptureListener(event)
* Returns: [Component][Component]

Capture **mousemove** event passing throught this component

      mousemoveCaptureListener: (event) ->
        super

Proceed only for valid event

        if event
          $ = @___runtime

Reset component state.

          @state = null

If component is grabbed then set the state to **active**.

          if $.grab
            @state = 'active'

Create **drag** Event and broadcast it to this component if drag event is enabled,

            if @events?.drag
              @broadcastEvent new Event
                type:'drag', x:event.x, y:event.y

setting the drag offset.

                offsetX: event.x - ($.dragEvent?.x or $.grabEvent?.x or 0)
                offsetY: event.y - ($.dragEvent?.y or $.grabEvent?.y or 0)

Otherwise, set the state to the name of the first matching region in order.

          else if regions = event.regions
            @state = (if regions.hover then 'hover' else if regions.normal then 'normal')

        return this

#### PARAMETERS
**event**
* Type: [Event][Event]

---

### #mousedownListener(event)
* Returns: [Component][Component]

Receive **mousedown** event.

      mousedownListener: (event) ->
        super

Proceed only for valid event

        if event

If component is in active state and **grab** event is enabled then grab this component.

          if (@state is 'active') and @events?.grab
            ($ = @___runtime).grab = true

Create **grab** event and deliver it to this component.

            $.dragEvent = null
            @broadcastEvent new Event
              type:'grab', x:event.x, y:event.y

        return this

#### PARAMETERS
**event**
* Type: [Event][Event]

---

### #dragCaptureListener(event)
* Returns: [Component][Component]

Capture **drag** events passing through this component

      dragCaptureListener: (event) ->

Proceed only for valid event

        if event

Save the event and localize event coordinates.

          @___runtime.dragEvent = event
          localizeEventCoordinates event, @origin

        return this

#### PARAMETERS
**event**
* Type: [Event][Event]

---

### #grabCaptureListener(event)
* Returns: [Component][Component]

Capture **grab** events passing through this component.

      grabCaptureListener: (event) ->

Proceed only for valid event

        if event

Save the event and localize event coordinates.

          @___runtime.grabEvent = event
          localizeEventCoordinates event, @origin

        return this

#### PARAMETERS
**event**
* Type: [Event][Event]

---

* Returns: [Component][Component]

Capture **release** events passing through this component.

      releaseCaptureListener: (event) ->

Proceed only for valid event

        if event

Save the event and localize event coordinates.

          @___runtime.releaseEvent = event
          localizeEventCoordinates event, @origin

        return this

#### PARAMETERS
**event**
* Type: [Event][Event]

---

* Returns: [Component][Component]

#### #dragListener(event)
* Returns: [Component][Component]

**drag** event receiver stub.

      dragListener: -> this

#### PARAMETERS
**event**
* Type: [Event][Event]

---

### #grabListener(event)
* Returns: [Component][Component]

**grab** event receiver stub.

      grabListener: -> this

#### PARAMETERS
**event**
* Type: [Event][Event]

---
### #releaseListener(event)
* Returns: [Component][Component]

**release** event receiver stub.

      releaseListener: -> this

#### PARAMETERS
**event**
* Type: [Event][Event]

[Parent]: ./index.litcoffee
[Element]: ./element.litcoffee
[Component]: ./component.litcoffee

# CLASS: Component
* Extends: [Element][Element]
* Parent: [Index][Parent]

---

    module.exports = class Component extends require './element'

## CONSTRUCTOR

### new Component()

Creates Component instance.

      constructor: -> super

#### PARAMETERS
* **args** - named arguments

---

## PROPERTIES

---

## METHODS

[Parent]: ./index.litcoffee
[Element]: ./element.litcoffee