2013-05-08 2 views
4

이것은 AngularJS 앱을위한 것입니다. 서비스에 의존하는 사용자 지정 지시문이 있습니다.AngularJS : 사용자 작업이 모델과 DOM에 모두 영향을주는 경우

내가 정말로 궁금한 점은 모델과 DOM에 모두 영향을주는 사용자 작업을 다루는 "각도 방식"입니다. 일부 예제 코드 :

HTML :

<form foo-places> 
    <!--other stuff --> 
    <span ng-repeat="place in places"> 
     <button ng-click="removePlace(place)">remove {{place}}</button> 
    </span>   
</form> 

JS : 사용자가 (버튼을 클릭하여) 장소를 제거

angular.module('foo.directives', []).directive('fooPlaces', 
function(placesService) { 
    return { 
     controller : function($scope) { 
      $scope.places = placesService.places; 
        $scope.removePlace = function(name) { 
       placesService.removePlace(name); 
      }; 
      $scope.$on('placesChanged', function() { 
       $scope.places = placesService.places; 
      }); 
     }, 
     link : function($scope, element, attrs) { 
       //code to do stuff when user removes a place 
     } 
    } 
}) 

, 나는 또한 DOM과 혼란에 물건을 할 필요가 예를 들어 창을 맨 위로 스크롤하는 등의 작업을 할 수 있습니다. 컨트롤러에서 모델을 다루는 함수를 갖고있는 것이 이상하게 느껴지고 DOM 함수를 처리하는 지시문에서 또 다른 함수가됩니다.하지만 둘 다 같은 사용자를 기반으로합니다 동작.

나는 이것을 과소 평가 했는가? 모델과 DOM을 모두 다루는 단일 사용자 작업을 어떻게 처리해야합니까?

+0

장소 모음에서 'scope. $ watch'를 사용하는 UI 변경 사항을 처리하기 위해 별도의 지시문을 사용할 수 있습니다. 그렇게하면 컬렉션에 대한 모든 변경 사항을 UI에 보편적으로 업데이트 할 수 있으며 작업 범위에 적합한 마크 업 요소에 해당 지시문을 추가하면됩니다. 두 가지 방법으로 모두 수행했으며 시계 추가는 섞기보다 깔끔하다고 생각합니다. 링크 함수에서 jQuery 또는 다른 dom 조작 항목을 사용하여 모델을 변경합니다. – Sounten

+0

@ 샘턴 - 당신이 제안한대로 $ 시계를 추가하는 것이 더 깔끔하다는 것에 동의하는지 모르겠습니다. 하지만 내가 아는 것은 기본적인 예제를 넘어서서 anglejs에 대해 생각한 것이 항상 실제 물건을 만드는 가장 좋은 방법과 일치하지 않는다는 것입니다. 의견을 보내 주셔서 감사합니다. 나는 그걸 가지고 놀 것이다. – BjornJohnson

답변

4

AngularJS를 다룰 때 "모델이 진실의 단일 소스입니다."라는 말을 들었을 것입니다. 이 부분을 이해하면 나머지 부분은 쉽게 제자리에 떨어집니다. 이것은 "각도 방식"입니다.

사용자가 상호 작용할 때 - 그는 DOM이나보기와 상호 작용하지 않습니다. 그는 모델과 상호 작용하고 있습니다. 뷰 자체는 모델의 "뷰"일뿐입니다. 같은 모델에 대한 다른 견해가있을 수 있습니다 - 이것이 모델이 진실의 단일 소스라는 이유입니다. 이제는 사용자가 상호 작용할 때 모델을 변경하는 각도를 허용합니다. 이러한 변경을 수행하고 모델이 변경 되었기 때문에 뷰의 시작은 모델의 변경된 상태를 반영합니다.

또한 관심사의 분리를 강조하기 위해 지시문은 서비스를 직접 다루지 않아야합니다. 지시문은 DOM의 조각으로, 이는 뷰의 일부임을 의미합니다. 서비스는 일반적으로 비즈니스 논리와 관련이 있거나 모델을 나타냅니다. MVC 또는 MVVM에서는 뷰를 모델과 직접 상호 작용하지 않습니다. 항상 ViewModel 또는 Controller를 사용합니다. 이렇게하면 종속성이 최소한으로 유지됩니다.

사용자의 ScrollToTop은 사용자가 컨트롤러에서 호출하는 서비스 일 수 있습니다 (각도로 서비스 인 참조). 그것은 당신이 원하는 것을하지는 않지만, 당신의 서비스를 구현할 필요가있는 스크롤 서비스입니다.

편집 :

당신은 일반적으로 해달라고 서비스에 DOM manipulately 물건을 명확히합니다. 서비스에서 DOM 조작 요소를 고려할 수있는 시나리오는 특정 HTML 요소에 속하지 않고 앱 수준에서 발생해야하는 경우입니다.

설명해 드리겠습니다. 예를 들어 대화창/모달 창과 같은 것을하려고하는 경우 - angularJS에서는 일반적인 UI 구성 요소이므로 지시문을 사용하는 것이 이상적이라고 생각할 수 있습니다. 그러나 AngularJS에 대한 지침은 요소와 관련된 것입니다. 항상 지시어를 html 요소와 연결합니다. 그러나 우리가 보았 듯이, 대화는 당신이 요소에 붙이는 것이 아니라 오히려 세계적인 것입니다. 이는 아마 예외 일 것입니다.

$window$document 관련 항목 (예 : 스크롤)에 대해서도 마찬가지입니다.이들은 특정 요소에 속하지 않습니다 (div 안에 스크롤하려는 경우 지시어 여야 함). 따라서 서비스가되어야합니다. 또한 이것은 아마도 지침에 삽입 할 수있는 서비스입니다. 지시어가 트리거 될 때마다 scrollToTop을 누르거나 대화 상자를 열려고한다고 말하십시오. 이런 종류의 서비스를 지침에 주입 할 수 있습니다. 지시문에 삽입하면 안되는 서비스 종류는 비즈니스 논리와 관련된 서비스입니다. 지시문을 재사용 가능한 UI 구성 요소로 취급하십시오.

물론 DSL을 만드는 더 높은 수준의 구성 요소 (만들려는 구성 요소)를 만들 수 있지만 그때 당신은 무엇을하고 있는지 정확하게 알아야합니다. 그때까지, 나는 당신이 평범한 구 컨트롤러, 지침 및 서비스를 고수하고 각각이 자신의 우려를 관리 할 것을 제안한다.

+0

감사합니다. 나는 당신이 특히 "귀하의 진술은 드물게 서비스에 직접 대처해서는 안됩니다."라는 질문을 통해 제게 관심사의 분리에 대해 명확하게 설명해주었습니다. 몇 가지 후속 질문이 있습니다. 만약 내가 "DOM 조작 - ish"다른 것들을하고 싶었 을까? 그 잠재적 인 것들 각각에 대해 서비스를 만들 것을 제안 하시겠습니까? 당신이 상상할 수 있듯이, 많은 질문은 "지시문에서 DOM 조작 만"에 의해 주도됩니다. 서비스에서 DOM과 관련된 작업을 수행하면이 문제가 발생합니까? 아니면 내가 지금 서비스를 오해하고 있는가? :) – BjornJohnson

+0

비즈니스 로직을 다루는 서비스를 삽입하지 말고 대화 또는 doc과 같은 항목을 처리 할 때 허용하도록하는 제안뿐만 아니라 지시문에 맞지 않는 앱 수준/전역 정보를 둘러싼 훌륭한 설명과 설명 레벨 스크롤링. 정말 고마워. – BjornJohnson

관련 문제