/*
 * Copyright 2015-present Open Networking Laboratory
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

/*
 ONOS GUI -- SVG -- Zoom Service
 */
(function () {
    'use strict';

    // configuration
    var defaultSettings = {
        zoomMin: 0.05,
        zoomMax: 10,
        zoomEnabled: function (ev) { return true; },
        zoomCallback: function () {}
    };

    // injected references to services
    var $log;

    angular.module('onosSvg')
        .factory('ZoomService', ['$log',

        function (_$log_) {
            $log = _$log_;

/*
            NOTE: opts is an object:
            {
                svg: svg,                       D3 selection of <svg> element
                zoomLayer: zoomLayer,           D3 selection of <g> element
                zoomEnabled: function (ev) { ... },
                zoomCallback: function () { ... }
            }

            where:
                * svg and zoomLayer should be D3 selections of DOM elements.
                    * zoomLayer <g> is a child of <svg> element.
                * zoomEnabled is an optional predicate based on D3 event.
                    * default is always enabled.
                * zoomCallback is an optional callback invoked each time we pan/zoom.
                    * default is do nothing.

            Optionally, zoomMin and zoomMax also can be defined.
            These default to 0.25 and 10 respectively.
*/
            function createZoomer(opts) {
                var cz = 'ZoomService.createZoomer(): ',
                    d3s = ' (D3 selection) property defined',
                    settings = angular.extend({}, defaultSettings, opts),
                    zoom = d3.behavior.zoom()
                        .translate([0, 0])
                        .scale(1)
                        .scaleExtent([settings.zoomMin, settings.zoomMax])
                        .on('zoom', zoomed),
                    fail = false,
                    zoomer;

                if (!settings.svg) {
                    $log.error(cz + 'No "svg" (svg tag)' + d3s);
                    fail = true;
                }
                if (!settings.zoomLayer) {
                    $log.error(cz + 'No "zoomLayer" (g tag)' + d3s);
                    fail = true;
                }

                if (fail) {
                    return null;
                }

                // zoom events from mouse gestures...
                function zoomed() {
                    var ev = d3.event.sourceEvent;
                    if (settings.zoomEnabled(ev)) {
                        adjustZoomLayer(d3.event.translate, d3.event.scale);
                    }
                }

                function adjustZoomLayer(translate, scale) {
                    settings.zoomLayer.attr('transform',
                        'translate(' + translate + ')scale(' + scale + ')');
                    settings.zoomCallback(translate, scale);
                }

                zoomer = {
                    panZoom: function (translate, scale) {
                        zoom.translate(translate).scale(scale);
                        adjustZoomLayer(translate, scale);
                    },

                    reset: function () {
                        zoomer.panZoom([0,0], 1);
                    },

                    translate: function () {
                        return zoom.translate();
                    },

                    scale: function () {
                        return zoom.scale();
                    },

                    scaleExtent: function () {
                        return zoom.scaleExtent();
                    }
                };

                // apply the zoom behavior to the SVG element
                settings.svg && settings.svg.call(zoom);
                return zoomer;
            }

            return {
                createZoomer: createZoomer
            };
        }]);

}());
