2014-01-30 4 views
0

나는 angularjs를 처음 사용하고 있으며, 많은 자료를 읽고, 다양한 기사와 튜토리얼 및 비디오를 통해이 내용을 파악하는 데 도움이되는 비디오를 읽었습니다. 두 지침이 서로 정보를 교환하려고합니다. 내가 뭘 하려는지 정말 단순화 된 버전은 odetocode (http://odetocode.com/blogs/scott/archive/2013/09/11/moving-data-in-an-angularjs-directive.aspx)에서 k scott allen이 ng-controller 특성을 가진 div로 그의 지시문을 아름답게 감쌌다는 것입니다.angularjs directive comunication

나는 약간 더 복잡한 테스트를 진행하고 있는데, 내가 언급 한 코드와 비슷하게 작동하도록 노력 중이다.

각 지시어에 대한 실제 템플릿에 ng-controller 속성을 나열하면 두 개의 지시문이 서로 이야기합니다. 그것은 작동하지만, 나는 그것이 옳다고 생각하지 않는다. 실제 컨트롤러 코드는 각 지시어에 대해 한 번씩 두 번 실행됩니다. 컨트롤러를 두 개의 지시문을 감싸는 div로 이동할 때 두 지시문이 상호 작용을 멈 춥니 다 (위치 선택기 템플릿의 change 이벤트가 컨트롤러의 파크를 변경하지 않음). 나는 그것이 그 범위와 관련이 있다고 확신한다. 누군가가 올바른 방향으로 나를 가리킬 수 있거나 정보를 찾아야하는 곳이면 많은 도움이 될 것입니다. 여기

내 바이올린은 내 코드 http://jsfiddle.net/jgbL9/25/

<div ng-app="myApp"> 
    <location-selector ></location-selector ><br/> 
    <portal-map ></portal-map > 
</div> 



    var App = angular.module('myApp', ['ngResource']); 

    App.directive('locationSelector',['parkList', function(parkList) { 
     return { 
     restrict: 'E', 
     scope: { 
      parkId : '=', 
      parkName : '=' 
     }, 
     template: '<select ng-controller="portalMapCtrl"'+ 
      ' ng-model="listParks" ng-change="changePark()" '+ 
      ' park-id="parkId" park-name="parkName" ' + 
      ' ng-options="park as park.attributes.NAME for park in Parks" >'+ 
      '</select>', 
     link: function (scope,element,attrs){ 
      parkList.getListFromGIS().success(function(data) { 
      scope.Parks = data.features; 
      }); 
     } 
     }; 
    }]); 

    App.directive('portalMap', function(){ 
     return { 
     restrict: 'E', 
     scope:{ 
      parkId: "=", 
      parkName: "=" 
     }, 
     template: '<style type="text/css" media="screen">'+ 
      '#mapCanvas {height: 500px; width:75%; border:thin black solid; }'+ 
      '</style>'+ 
      '<div id="mapCanvas" park-id="parkId" park-name="parkName" ng-controller="portalMapCtrl" ></div>' 
     } 
    }); 


    App.controller('portalMapCtrl',['$scope','parkList', function($scope, parkList){ 
     var map = {}; 
     var STREETMAPSERVICE = "https://gis.odot.state.or.us/ArcGIS/rest/services/BASEMAPS/Basemap_Streets/MapServer"; 
     var FOTOSSERVICE = "https://maps.prd.state.or.us/arcgis/rest/services/ESRI_TEST/MapServer?f=jsapi"; 
     var UTILSSERVICE = "http://gis.prd.state.or.us/ArcGIS/rest/services/OPRDAssets/MapServer"; 
     var UTILSSERVICE_PARKLAYER = 0; 
     var UTILSSERVICE_STRUCTUREPOLY = 7; 
     var UTILSSERVICE_SURFACE = 11; 
     var UTILSSERVICE_PARCELS = 12; 
     var timer; 
     var ALL_LAYERS = [UTILSSERVICE_PARKLAYER,UTILSSERVICE_STRUCTUREPOLY,UTILSSERVICE_SURFACE,UTILSSERVICE_PARCELS]; 
     $scope.parkId = 0; 
     $scope.parkName = ""; 
     $scope.changePark = function(){ 
     require(["esri/SpatialReference","esri/geometry/Polygon"], 
      function(SpatialReference,Polygon){ 
      console.log('change park'); 
      $scope.parkId = $scope.listParks.attributes.PARK_HUB_ID; 
      $scope.parkName = $scope.listParks.attributes.NAME; 
      parkList.getParkFromGIS($scope.parkId).then(function(data){ 
       var x = data.data; 
       var y = x.features[0]; 
       var rings = y['geometry']; 
       var poly = new Polygon(rings); 
       var xtnt = poly.getExtent(); 
       var sr = new SpatialReference({wkid:2992}); 
       xtnt.setSpatialReference (sr); 
       map.setExtent(xtnt,true); 
      }); 
      }); 
     }; 
     function addService(srvc, srvcType, lyrId){require([ 
       "esri/layers/ArcGISTiledMapServiceLayer", 
       "esri/layers/ArcGISDynamicMapServiceLayer", 
       "esri/layers/ImageParameters"], function(Tiled,Dynamic,Parameters){ 
      var mapService = {}; 

      if(srvcType == 'Tiled'){ 
      mapService = new Tiled(srvc); 
      }else{ 
      var imageParameters = new Parameters(); 
      imageParameters.layerIds = lyrId; 
      imageParameters.transparent = true; 
      mapService = new Dynamic(srvc,{"imageParameters":imageParameters}); 
      } 
      map.addLayer(mapService); 
      }); 
     } 

     function createMap(){ 
     require(["esri/map"],function(Map){ 
      console.log('create map'); 
      map = new Map("mapCanvas"); 
      addService(STREETMAPSERVICE,'Tiled'); 
      addService(FOTOSSERVICE,'Tiled'); 
      addService(UTILSSERVICE,'Dynamic',ALL_LAYERS); 
     }); 
     } 
     createMap(); 

    }]); 


    App.factory('parkList',['$http', function($http) { 
    return { 
     getListFromGIS: function() { 
     var myUrl = 'http://maps.prd.state.or.us/arcgis/rest/services/ESRI_TEST/MapServer/0/query?where=OBJECTID+%3E+0&geometryType=esriGeometryEnvelope&spatialRel=esriSpatialRelIntersects&outFields=PARK_HUB_ID%2CNAME&returnGeometry=false&&returnIdsOnly=false&returnCountOnly=false&orderByFields=NAME&returnZ=false&returnM=false&returnDistinctValues=true&f=pjson&callback=JSON_CALLBACK'; 
     return $http ({ url: myUrl, method: 'JSONP'}); 
     }, 
     getParkFromGIS: function (id){ 
      var myUrl = "http://maps.prd.state.or.us/arcgis/rest/services/ESRI_TEST/MapServer/0/query?where=PARK_HUB_ID%3d"+id+"&f=pjson&callback=JSON_CALLBACK"; 
      return $http ({ url: myUrl, method: 'JSONP'}); 
     }, 
     JSON_CALLBACK: function(data) {} 
    }; 
    }]); 

(이 각 지침의 템플릿에 나와있는 NG-컨트롤러와 함께 작동하는 코드)를 표시한다.

내 코드 구조 나 코드 선택에 대해 다른 의견이나 제안을 보내 주시면 감사하겠습니다. 제가 언급했듯이, 배우면서 더 많은 재미를 배울 수 있습니다.

답변

0

귀하의 지침에서 분리 범위 (링크 기능에서 scope: { })로 인해 문제가 있다고 생각합니다.

지시어를 만드는 대신 응용 프로그램에 템플릿을 인라인하는 것이 좋습니다.

특히, locationSelector은 지시문을 만들기가 어려울 것입니다. 입력 요소를 컨트롤러가있는 요소의 일부로 만드는 것이 일반적으로 쉽습니다.

당신이 그 (것)들을 지시문을 사용하면 좋을 않은 경우, 나는 changePark 기능에 listParts 값을 전달 좋을 것 :

<select ... ng-change="changePark(listParks)" ...> 
+0

그래, 내 지시에 분리 범위이었다. ㅎ. 나는 더 많은 독서가 분명하게있다. 선택기에서 지시문 + 링크에서 범위를 제거하고 컨트롤러에 데이터로드를 추가하면 완벽하게 작동합니다. 도와 줘서 고마워. – timgogl