###*
# Adds the 'done' class to the form section to allow the user to see which sections are completed
# @class FormSection
# @type Directive
###
class CanContinue extends Directive('hn.enterprise')
    constructor: () ->
        return {
            # attrs:
            # canContinue       section ID to look for form elements
            # validClass        class to apply when all valid
            # invalidClass      class to apply when section invalid
            link: (scope, elem, attrs) ->
                forForm = scope[attrs.forForm]
                findFields = (elem) ->
                    elem
                        .find("[required], [ng-required]")
                        .map( (i, e) ->
                            $(e).attr('name')
                        )
                        .toArray()
                        .map( (i) ->
                            () -> forForm[i].$valid
                        )
                fields = findFields($(elem).parents('section.form-section'))
                if attrs.canContinue
                    eler = $("#"+attrs.canContinue)
                    additionalFields = findFields(eler)
                    fields = fields.concat(additionalFields)


                scope.$watchGroup(fields, (newValues) ->
                    isValid = _.every(newValues)
                    if isValid
                        elem.addClass(attrs.validClass || 'valid')
                        elem.removeClass(attrs.invalidClass || 'invalid')
                    else
                        elem.addClass(attrs.invalidClass || 'invalid')
                        elem.removeClass(attrs.validClass || 'valid')
                )
        }

class FloatingLabel extends Directive('hn.enterprise')
    constructor: () ->
        return {
            link: (scope, elem) ->
                isEmpty = () ->
                    ctrl = angular.element(elem).data('$ngModelController')
                    return ctrl.$isEmpty(ctrl.$modelValue)

                scope.$watch(isEmpty, (value) ->
                    elem.parents('.float-group').toggleClass("with-value", !value)
                , true)
        }

# TODO: Remove. Use UI Boostrap Rating directive
class StarRating extends Directive('hn.enterprise')
    constructor: ->
        return {
            restrict: 'E'
            scope:
                value: "=value"
            replace: true
            template: """<span class="star-rating"><span ng-repeat="n in [1,2,3,4,5]" ng-class="{
                'glyphicon-star': n <= value,
                'glyphicon-star-empty': n > value
                }" class="glyphicon"></span></span>"""
            link: (scope) ->
                scope.value = Math.round(scope.value)
        }


class Feedback extends Directive('hn.enterprise')
    constructor: ($modal) ->
        return {
            link: (scope, elem) ->
                elem.on('click', () ->
                    modal = $modal.open({
                        templateUrl: '/modules/enterprise/views/feedback_modal.html'
                        ### @ngInject ###
                        controller: ($scope, $state, App, Flash) ->
                            vm = @

                            vm.feedback = {
                                context: $state.href($state.current.name, $state.params, {absolute: true})
                            }

                            vm.submit = () ->
                                App.feedback(vm.feedback).$promise.then(() ->
                                    Flash('Feedback Submitted. Thank you!', 'success')
                                )

                                $scope.$close()
                            return
                        controllerAs: 'vm'
                        windowClass: 'feedback'
                    })
                )
        }


class Help extends Directive('hn.enterprise')
    constructor: ($modal, Branding, APP_CONFIG) ->
        return {
            link: (scope, elem) ->
                elem.on('click', () ->
                    modal = $modal.open({
                        templateUrl: '/modules/enterprise/views/help.html'
                        windowClass: 'help'
                    })
                )
        }


class WhenInvisible extends Directive('hn.enterprise')
    constructor: ($parse) ->
        return {
            link: (scope, elem, attrs) ->
                $(window).scroll( () ->
                    invisible = elem[0].getBoundingClientRect().bottom < 0
                    if invisible
                        scope.$evalAsync( () ->
                            $parse(attrs.whenInvisible)(scope)
                        )
                )
        }

class WhenVisible extends Directive('hn.enterprise')
    constructor: ($parse) ->
        return {
            link: (scope, elem, attrs) ->
                $(window).scroll( () ->
                    visible = elem[0].getBoundingClientRect().bottom >= 0
                    if visible
                        scope.$evalAsync( () ->
                            $parse(attrs.whenVisible)(scope)
                        )
                )
        }

class BackButton extends Directive('hn.enterprise')
    constructor: ($state, $rootScope) ->
        return {
            scope: true
            # TODO: remove hide class and fix this thing!
            template: """<a href class='btn back-button hide'
                                 ui-sref='{{routeString}}'>
                            <span class='glyphicon glyphicon-menu-left'></span>
                            {{text}}
                         </a>
                      """
            link:
                pre: (scope, elem) ->
                    scope.routeString = '^'
                    elem.hide()

                    changeButton = () ->
                        if $state.current.data? and $state.current.data.backButton?
                            elem.show()
                            backButton = $state.current.data.backButton
                            scope.text = backButton.text || 'Back'
                            params = backButton.params($state.params)
                            scope.routeString = backButton.state + '(' + params + ')'
                        else
                            elem.hide()
                    changeButton()
                    $rootScope.$on('$stateChangeSuccess', changeButton)
        }


class SubSidebar extends Directive('hn.enterprise')
    constructor: () ->
        return {
            transclude: true
            template: "<div ng-transclude></div>"
            link: (scope, elem) ->
                $(elem).addClass('sub-sidebar')

                wrapper = $(elem).parents('.wrapper')

                wrapper.css('marginLeft', 350)
                scope.$on('$destroy', () ->
                    wrapper.css('marginLeft', 80)
                )

        }


class RepeatList extends Directive('hn.enterprise')
    constructor: () ->
        return {
            compile: (elem, attrs) ->
                delimiter = attrs.delimiter or ', '
                delimiterHtml = "<span ng-show='!$last'>#{delimiter}</span>"

                html = elem.html().replace(/(\s*$)/i, (whitespace) ->
                    return delimiterHtml + whitespace
                )

                elem.html(html)

            priority: 1001
            restrict: "A"
        }
