/**
 *
 */
'use strict';
define(function() {
  /**
   * Unit Ctrl
   * @param $scope
   * @param UnitFactory
   * @constructor
   */
  var BaseMapCtrl = function(
    $scope,
    BaseMapFactory,
    ThumbnailFactory,
    SridFactory,
    $timeout,
    gaJsUtils,
    gaDomUtils,
    $filter,
    DataStoreFactory
  ) {
    function checkBackground() {
      var ind, bgs;
      if ($scope.edit_resource.type === 'COMPOSED') {
        bgs = $scope.edit_resource.backgrounds;
        for (ind = 0; ind < bgs.length; ind++) {
          bgs[ind].minResolution = gaJsUtils.scaleToResolution(
            bgs[ind].minscale
          );
          bgs[ind].maxResolution = gaJsUtils.scaleToResolution(
            bgs[ind].maxscale
          );
        }
      }
    }

    /**
     * Fond de plan ArcGis
     */
    // Récupération de toutes les sources de données ArcGis
    $scope.esriDatastoreNames = [];
      DataStoreFactory.getEsriDataStores().then(
        (res) => {
          for (const datastore of res.data) {
            $scope.esriDatastoreNames.push(datastore.name);
          }
        }
    );

    // Au changement de dataStoreEsri, on recharge la dual-list-box
    $scope.esriDatastoreChange = () => {
      $scope.edit_resource.editTypeList = {
        leftDisplayAttribute: 'name',
        rightDisplayAttribute: 'name',
        source: 'right',
        leftTitle: $filter('translate')('rulecfg.common.selectedLayers'),
        rightTitle: $filter('translate')('rulecfg.snapon.availablelayers'),
        removeDuplicates: true
      };
      if($scope.edit_resource.esriDatastore) {
        DataStoreFactory.getLayersDataByDatastore(
            $scope.edit_resource.esriDatastore, "name").then(
            (res) => {
              // Fill the right data of DualListBox
              $scope.edit_resource.editTypeList.rightData = [];
              for (const layer of res.data) {
                $scope.edit_resource.editTypeList.rightData.push(
                    {
                      name: layer.name,
                      id: layer.id
                    });
              }
              $scope.$broadcast('changeDualListBoxData');
            }
        );
      }
    };
    // À l'enregistrement, récupère les couches du fond de plan depuis la dualListBox
    const buildDataForArcgisBaseMap = () => {
      if($scope.edit_resource.type === 'ARCGIS' && $scope.edit_resource.esriDatastore) {
        $scope.edit_resource.layers = $scope.edit_resource.editTypeList.leftBackupData;
      }
    };


    $scope.fileNameChanged = function(a) {
      var firstFile = a.files[0];

      var fd = new FormData();
      fd.append('file', firstFile);

      ThumbnailFactory.uploadprocess(fd).then(function(data) {
        $scope.edit_resource.thumbnail = firstFile.name;

        try {
          $scope.$apply();
        } catch(err) {}
      });
    };

    /**
     * Create or update the Unit
     */
    $scope.srids = SridFactory.sridsList;
    $scope.editBaseMap = function() {
      gaDomUtils.showGlobalLoader();
      if (
        $scope.edit_resource.type === 'WMTS' &&
        $scope.edit_resource.url &&
        $scope.edit_resource.layer &&
        $scope.edit_resource.projection &&
        $scope.edit_resource.TileMatrixSet
      ) {
        var capabilities = $scope.edit_resource.url;
        var url = new URL(angular.copy(capabilities));

        if ($scope.edit_resource.key) {
          url.searchParams.append('KEY', $scope.edit_resource.key);
          //capabilities += "KEY=" + $scope.edit_resource.key;
        }

        url.searchParams.append('service', 'WMTS');
        url.searchParams.append('request', 'GetCapabilities');
        url.searchParams.append('version', '1.0.0');
        // capabilities += "&service=WMTS&request=GetCapabilities&version=1.0.0";

        var parser = new ol.format.WMTSCapabilities();
        var xhr = new XMLHttpRequest();
        xhr.open('GET', url, true);
        xhr.onload = function(e) {
          if (xhr.readyState === 4) {
            if (xhr.status === 200) {
              var result = parser.read(e.srcElement.response);
              $scope.edit_resource.capabilities = result;
              if ($scope.isNewResource) {
                $scope.edit_resource.order = $scope.currentResources.length + 1;
                BaseMapFactory.add($scope.edit_resource).then(function() {
                  $scope.isNewResource = false;
                });
              } else {
                BaseMapFactory.update(
                  $scope.edit_resource,
                  $scope.oldcopy &&
                    $scope.oldcopy.name &&
                    $scope.oldcopy.name !== $scope.edit_resource.name
                    ? $scope.oldcopy.name
                    : ''
                ).finally(gaDomUtils.hideGlobalLoaderAfterTimeout);
              }
            } else {
              gaDomUtils.hideGlobalLoaderAfterTimeout();
              require('toastr').error(xhr.statusText);
              console.error(xhr.statusText);
            }
          }
        };
        xhr.onerror = function(e) {
          gaDomUtils.hideGlobalLoaderAfterTimeout();
          require('toastr').error(xhr.statusText);
          console.error(xhr.statusText);
        };
        xhr.send(null);
      } else {
        // COMPOSED
        checkBackground();
        // ARCGIS
        buildDataForArcgisBaseMap();

        if ($scope.isNewResource) {
          $scope.edit_resource.order = $scope.currentResources.length + 1;
          BaseMapFactory.add($scope.edit_resource).then(function() {
            $scope.isNewResource = false;
          }).finally(gaDomUtils.hideGlobalLoaderAfterTimeout);
        } else {
          BaseMapFactory.update(
            $scope.edit_resource,
            $scope.oldcopy &&
              $scope.oldcopy.name &&
              $scope.oldcopy.name !== $scope.edit_resource.name
              ? $scope.oldcopy.name
              : ''
          ).finally(gaDomUtils.hideGlobalLoaderAfterTimeout);
        }
      }
    };
    
    $scope.saveChangedOrder = () => {
      BaseMapFactory.updateAll($scope.currentResources).then(function(res) {
        $scope.currentResources = BaseMapFactory.resources.basemaps;
      });
    };

    // Dans le cas d'un changement de type de fond de plan
    $scope.$watch('edit_resource.type', function(newval) {
      if (
        newval === 'WMTS' &&
        angular.isUndefined($scope.edit_resource.opacity)
      ) {
        $scope.edit_resource.opacity = 100;
      }
    });

    $scope.changedProjection = function(newval) {
      if (
        newval &&
        $scope.edit_resource &&
        $scope.edit_resource.type === 'WMTS' &&
        newval.indexOf('EPSG') !== -1
      ) {
        SridFactory.getbycode(newval).then(
          function(res) {
            if (res && res.data) {
              $scope.edit_resource.projectiondesc = res.data;
              proj4.defs(
                $scope.edit_resource.projection,
                $scope.edit_resource.projectiondesc
              );
              var projection = ol.proj.get($scope.edit_resource.projection);
              var extent = projection.getExtent();
              if (extent == null) {
                SridFactory.getExtentFromESPGIO(
                  newval.replace('EPSG:', '')
                ).then(function(res) {
                  var el = res.data.substring(
                    res.data.indexOf(
                      '<span class="caption">Projected bounds:</span><br />'
                    ),
                    res.data.indexOf(
                      '<span class="caption">WGS84 bounds:</span><br />'
                    )
                  );
                  var els = el.split('<br />');
                  var l = els[1].replace(' ', '');
                  var lo = l.substring(l.match(/\d+/).index);
                  var u = els[2].replace(' ', '');
                  var up = u.substring(u.match(/\d+/).index);
                  $scope.edit_resource.projectionExtent = [
                    parseFloat(lo.split(' ')[0]),
                    parseFloat(lo.split(' ')[1]),
                    parseFloat(up.split(' ')[0]),
                    parseFloat(up.split(' ')[1]),
                  ];
                });
              }
            }
          },
          function() {
            require('toastr').error('Map SRID description not found !');
          }
        );
      }
    };

    /**
     * Unit removal
     */
    $scope.removeBaseMap = function() {
      BaseMapFactory.remove($scope.edit_resource.name);
    };

    /**
     * Load loading
     */

    $scope.currentResources = BaseMapFactory.resources.basemaps;

    if (BaseMapFactory.resources.basemaps.length == 0) {
      BaseMapFactory.get().then(function(res) {
        $scope.currentResources = BaseMapFactory.resources.basemaps;
      });
    }

    /**
         EditList Directive configuration
         */
    $scope.editListCfg = {
      dataModule: 'model',
      resource_type: 'basemap',
      cols: ['type', 'name'],
      removeFunction: $scope.removeBaseMap,
      allowReorder: true,
      saveChangedOrder: $scope.saveChangedOrder,
    };

    $scope.validForm = {};
    $scope.validateName = function() {
      var actualName = $scope.edit_resource.name;
      $scope.$watch(
        'edit_resource.name',
        function(name) {
          $scope.nameExists =
            $scope.currentResources
              .map(function(r) {
                return r.name;
              })
              .indexOf(name) != -1;
          if (!$scope.isNewResource && $scope.edit_resource && $scope.edit_resource.name == actualName)
            $scope.nameExists = false;
          $scope.validForm.name = !$scope.nameExists;
        },
        1
      );
    };

    /**
     * GESTION DES FONDS DE PLAN COMPOSES
     */

    $scope.composedws = {};
    $scope.composedws.obj = {};
    $scope.composedws.obj.modelMax = 100;
    $scope.composedws.nok = function(obj) {
      if (obj == undefined) obj = $scope.composedws.obj;
      if (obj.name == undefined || obj.name.length == 0) return true;
      if (
        obj.minscale != undefined &&
        obj.maxscale != undefined &&
        parseInt(obj.minscale) > parseInt(obj.maxscale)
      )
        return true;

      return false;
    };

    $scope.addBgToCOmposed = function() {
      var bg = angular.copy($scope.composedws.obj);
      bg.name = bg.name.name;
      if ($scope.edit_resource.backgrounds == undefined)
        $scope.edit_resource.backgrounds = [];
      $scope.edit_resource.backgrounds.push(bg);
    };

    /**
     * Supprime une couche d'un fond de plan composé
     * @see modal.basemap.html
     * @param index rang de la couche à supprimer dans le tableau d'arrière-plans
     */
    $scope.removeBgToComposed = (index) => {
      $scope.edit_resource.backgrounds.splice(index, 1);
    };

    function bgItemChanged(bg, original) {
      if (Date.now() - $scope.composedws.lastchange < 500) {
        $timeout(function() {
          bgItemChanged(bg, original);
        }, 500);
      } else {
        if ($scope.composedws.nok(bg)) {
          //-- Quand les valeur d'échelle min et maxi sont incorrectes,
          //-- on rétabli les valeurs précédentes.
          bg.minscale = original.minscale;
          bg.maxscale = original.maxscale;
        }
      }
    }

    $scope.bgItemChanged = function(bg, original) {
      var dn = Date.now();
      if (
        $scope.composedws.lastchange == undefined ||
        dn - $scope.composedws.lastchange > 2000
      ) {
        $timeout(function() {
          bgItemChanged(bg, original);
        }, 500);
      }
      $scope.composedws.lastchange = dn;
    };

    $scope.changeBgPriority = function(bg, inc, ind) {
      /*
            var iBg;
            //-- Cherche le fond de plan dans la liste du fond de plan composé.
            for (var iBg=0; iBg < $scope.edit_resource.backgrounds.length; iBg++) {
                 if (bg==$scope.edit_resource[iBg]) {

                 }
            };
*/
      var tmp;
      tmp = $scope.edit_resource.backgrounds[ind + inc];
      $scope.edit_resource.backgrounds[ind + inc] = bg;
      $scope.edit_resource.backgrounds[ind] = tmp;
    };
  };

  BaseMapCtrl.$inject = [
    '$scope',
    'BaseMapFactory',
    'ThumbnailFactory',
    'SridFactory',
    '$timeout',
    'gaJsUtils',
    'gaDomUtils',
    '$filter',
    'DataStoreFactory',
  ];
  return BaseMapCtrl;
});
