angular.element와 document.getElementById 또는 스핀 (바쁜) 컨트롤이있는 jQuery 선택기


157

http://blog.xvitcoder.com/adding-a-weel-progress-indicator-to-your-angularjs-application/에 설명 된대로 스핀 컨트롤의 "Angularized"버전을 사용하고 있습니다.

표시된 솔루션에 대해 싫어하는 것 중 하나는 스핀 컨트롤을 DOM 요소에 효과적으로 연결하는 서비스에서 jQuery를 사용하는 것입니다. 각도 구성을 사용하여 요소에 액세스하는 것을 선호합니다. 또한 스피너가 서비스 내에서 연결 해야하는 요소의 ID를 "하드 코딩"하는 것을 피하고 대신 서비스의 단일 사용자를 설정하는 지시문을 사용하여 다른 서비스 사용자 또는 서비스 자체는 알 필요가 없습니다.

angular.element가 제공하는 것과 vs. 동일한 요소 ID의 document.getElementById가 제공하는 것과 어려움을 겪고 있습니다. 예. 이것은 작동합니다 :

  var target = document.getElementById('appBusyIndicator');

이 중 어느 것도 수행하지 않습니다.

  var target = angular.element('#appBusyIndicator');
  var target = angular.element('appBusyIndicator');

나는 분명히 명백하게 잘못해야 할 일을 분명히하고 있습니다! 아무도 도와 줄 수 있습니까?

위의 작업을 수행 할 수 있다고 가정하면 요소에 대한 jQuery 액세스를 대체하는 것과 비슷한 문제가 있습니다. 예 : $(target).fadeIn('fast'); 작동 angular.element('#appBusyIndicator').fadeIn('fast')하거나 작동 angular.element('appBusyIndicator').fadeIn('fast')하지 않습니다

누군가가 Angular "element"대 DOM 요소의 사용을 분명히하는 훌륭한 문서 예를 알려 줄 수 있습니까? Angular는 분명히 자체 속성, 메소드 등으로 요소를 "포장"하지만 원래 값을 얻는 것은 종종 어렵습니다. 예를 들어 <input type='number'>필드가 있고 사용자가 "-"(따옴표없이)를 입력 할 때 UI에 표시되는 원본 내용에 액세스하려는 경우 "type = number"는 Angular가 거부한다는 의미이므로 아무 것도 얻지 못합니다. 입력이 UI에 표시되어 있지만 입력하고 테스트하고 지울 수 있도록보고 싶습니다.

모든 답변 / 감사합니다.

감사.


5
angular.element는 jQuery를로드하는 경우 jQlite 객체 또는 jQuery 객체입니다.

답변:


226

그것은 다음 과 같이 작동 할 수 있습니다 :

var myElement = angular.element( document.querySelector( '#some-id' ) );

Document.querySelector()기본 Javascript 호출을 호출로 랩핑합니다 angular.element(). 따라서 사용 가능 /로드 여부에 따라 항상 jqLite 또는 jQuery 객체 의 요소를 가져옵니다 jQuery.

에 대한 공식 문서 angular.element:

jQuery 가 사용 가능한 경우 함수 angular.element의 별명입니다 jQuery. jQuery를 사용할 수없는 경우 "jQuery lite"또는 jqLite 라는 Angular 의 내장 하위 집합에 angular.element위임합니다 .jQuery

의 모든 요소 참조 Angular는 항상 jQuery 또는 jqLite(예 : 지시문 컴파일 또는 링크 함수의 요소 인수)로 래핑됩니다 . 그것들은 결코 원시 DOM참조 가 아닙니다 .

왜 사용해야하는지 궁금하다면 이 답변을document.querySelector() 읽으십시오 .


41
document.querySelector ( '# ...')를 단순히 document.getElementById ()를 사용하는 것보다 선호하는 이유는 무엇입니까?
카토

4
각도 요소에서이 작업을 수행 할 수도 있습니다. var elDivParent = angular.element (elem [0] .querySelector ( '# an-id')) ;, elem은 각도 요소입니다. 이렇게하면 요소 내부를 검색 할 수 있습니다. 단위 테스트에 유용합니다.
unludo 2018 년

4
@Kato 이 답변에 대한 추가 정보 . 희망이 도움이됩니다.
kaiser

Google Maps API를 사용하여 작동했습니다 var autocomplete = new google.maps.places.Autocomplete( $document[0].querySelector('#address'), { types: ['geocode'], componentRestrictions: {country: 'us'} } );. 팁 @kaiser에 감사드립니다. 어떤 이유로든지도 API는 내가 첫 번째 매개 변수에서 전달 한 것이 입력했을 때 입력이 angular.element(document.querySelector('#address'))아니라 모든 것이 잘 끝났다고 불평했습니다 .
nymo

49

아직 각도 요소 문서를 읽지 않았다면 jqLite가 지원하는 것과 jqlite가 각도에 내장 된 jquery의 서브셋이 아닌 것을 이해할 수 있습니다.

그 선택기가 작동하지 않습니다 때문에, 혼자 jqLite와 선택기 ID로는 지원되지 않습니다.

  var target = angular.element('#appBusyIndicator');
  var target = angular.element('appBusyIndicator');

따라서 :

  • jquery보다 jqLite를 단독으로 사용하지만 대부분의 상황에서 충분합니다.
  • 또는 jQuery 라이브러리 전체를 앱에 포함시키고 jquery가 필요한 곳에서 일반 jquery와 같이 사용하십시오.

편집 : jqLite보다 우선하려면 jQuery가 angularJS보다 먼저 로드되어야합니다 .

DOMContentLoaded 이벤트가 발생하기 전에로드 된 경우 실제 jQuery는 항상 jqLite보다 우선합니다.

편집 2 : 나는 전에 질문의 두 번째 부분을 놓쳤다.

와 문제는 <input type="number">, 내가 생각하는 그것, 그것은의 의도 된 행동 각도 문제가되지 않는 네이티브 HTML5 번호 요소입니다.

jquery .val()또는 raw .value속성 으로 검색하려고해도 숫자가 아닌 값을 반환하지 않습니다 .


2
우리는 전체 jQuery 라이브러리를 가지고 있습니다. 그렇지 않으면 위에서 설명한 $ 시나리오가 작동하지 않습니다. 내 질문은 전체 jQuery를 사용할 수 있지만 $가 작동하지만 angular.element가 작동하지 않는 이유에 대한 것입니다.
irascian 2016 년

1
angular.js 전후에 jQuery를 포함하고 있습니까? 각도 전에 포함되어야합니다 . ID별로 선택기는 : jQuery를 사용할 수와 작업 jsbin.com/ohumiy/1/edit
garst

1
그들은 다른 지시어 (즉, angular.element)에서 작업하여 id로 무언가에 액세스합니다. 동일한 jQuery와 동등한 기능이 직접 작동하는 이유를 이해하지 못하더라도 문제는이 컨트롤이 해당 요소에 첨부되어 작동하는 방식 인 것 같습니다. jQuery를 직접 사용하여 지시문 HAS에 닫는 태그가 있습니다-자체 닫는 태그가 작동하지 않습니다 (빈 화면 만 오류가 발생하지 않음).
irascian

2
내 두 번째 포인트에는 요소의 내용을 검색하는 데 사용할 수있는 view $ value와 같은 것이 있지만 입력 유형 = 숫자의 경우 사용자가 "-"를 입력 한 경우 비어 있습니다. 지시어에서 프로그래밍 방식으로 액세스 할 수 없지만 "-"가 여전히 UI에 있기 때문에 Angular가 시작하기 전에 요소의 $ rawInputValue와 같은 속성을 원합니다.
irascian

27
var target = document.getElementById('appBusyIndicator');

동일하다

var target = $document[0].getElementById('appBusyIndicator');

1
두 번째 예를 사용하여 종속성이 명시 적이며 조롱 할 수 있는지 확인하는 것이 좋습니다.
Luke

앵귤러 2 이상에서는 타이프 스크립트 기능에 더 의존합니다. 더 이상 이러한 것들에 대해 걱정할 필요가 없습니다 :)
Dasun

17

각도를 사용하는 것이 올바른 방법이라고 생각하지 않습니다. 프레임 워크 메소드가 존재하지 않으면 작성하지 마십시오! 이것은 프레임 워크 (여기에서 각도)가 이런 식으로 작동하지 않음을 의미합니다.

앵귤러를 사용하면 이와 같은 DOM (jquery 방법)을 조작해서는 안되지만 다음과 같은 각도 도우미를 사용해야합니다.

<div ng-show="isLoading" class="loader"></div>

또는 자신의 지시어 (자신의 DOM 구성 요소)를 작성하여 명령을 완전히 제어 할 수 있습니다.

BTW, http://caniuse.com/#search=queryselector querySelector는 잘 지원되므로 안전하게 사용할 수 있습니다.


2
당신 말이 맞아요 내가 수동으로 DOM을 조작해야한다고 생각한 경우의 90 % 이상이 필요를 제거하기 위해 코드를 리팩토링하고 결국 코드가 훨씬 깨끗했습니다.
Stephen Chung

17

누군가가 꿀꺽 꿀꺽 마시면 사용하면 오류가 표시 document.getElementById()되고 사용을 제안 $document.getElementById()하지만 작동하지 않습니다.

사용하다 -

$document[0].getElementById('id')

왜 각도가 배열을 주입합니까?
피터

16

$ document를 사용하여 요소에 액세스 할 수 있습니다 ($ document를 삽입해야 함)

var target = $document('#appBusyIndicator');
var target = $document('appBusyIndicator');

또는 각도 요소를 사용하면 다음과 같이 지정된 요소에 액세스 할 수 있습니다.

var targets = angular.element(document).find('div'); //array of all div
var targets = angular.element(document).find('p');
var target = angular.element(document).find('#appBusyIndicator');

1
find ()-태그 이름으로 조회로 제한
RJV

angular.element (document) .find ( '. someClass'); 완벽하게 작동합니다.
Nishant Baranwal

10

컨트롤러에 $ document를 삽입하고 원본 문서 대신 사용하십시오.

var myElement = angular.element($document[0].querySelector('#MyID'))

jquery 스타일 요소 랩이 필요하지 않으면 $ document [0] .querySelector ( '# MyID')가 DOM 객체를 제공합니다.


1
Angulars $ document 서비스 오버 헤드를 사용하는 대신 window.document를 직접 참조 할 수도 있습니다.
MatBee

5
물론
단위 테스트

나에게 분명하지 않다 : 나는이 경고를 얻는다 : 당신은 기본 문서 객체 대신 $ document 서비스를 사용해야하지만, 그것은 무엇을 의미합니까? 그것에 대한 문서가 있습니까? 감사!
realnot

@realnot 당신은 자바 스크립트의 어느 곳에서나 HTML DOM Document Object에 액세스 할 수 없습니다. w3schools.com/jsref/dom_obj_document.asp
Adamy

6

이것은 나를 위해 잘 작동했습니다.

angular.forEach(element.find('div'), function(node)
{
  if(node.id == 'someid'){
    //do something
  }
  if(node.className == 'someclass'){
    //do something
  }
});

3
요소가 정의되어 있지 않습니까? angular.element.find는 JQuery없이 당신을 시도하는 함수가 아닙니다.

3
이러지 마십시오. 다른 예 중 하나를 사용하십시오. 이것은 해시 테이블 조회 최적화를 전혀 사용하지 않습니다.
MatBee

4

카이저의 답변 개선 :

var myEl = $document.find('#some-id');

$document지시문 에 주사하는 것을 잊지 마십시오


21
element.find : 의 각도 문서에서 언급했듯이 find() - Limited to lookups by tag nameID에서는 작동하지 않습니다. 또한 추가 폐쇄가 )있습니다.
paaat

3

어쩌면 나는 여기에 너무 늦었지만 이것이 효과가 있습니다.

var target = angular.element(appBusyIndicator);

없음 appBusyIndicator, 일반 ID 값입니다.

뒤에서 일어나는 일 : (div에 적용되었다고 가정) (angular.js line no : 2769 이상에서 가져 왔습니다 ...)

/////////////////////////////////////////////
function JQLite(element) {     //element = div#appBusyIndicator
  if (element instanceof JQLite) {
    return element;
  }

  var argIsString;

  if (isString(element)) {
    element = trim(element);
    argIsString = true;
  }
  if (!(this instanceof JQLite)) {
    if (argIsString && element.charAt(0) != '<') {
      throw jqLiteMinErr('nosel', 'Looking up elements via selectors is not supported by jqLite! See: http://docs.angularjs.org/api/angular.element');
    }
    return new JQLite(element);
  }

페이지에 jQuery가 없으면 기본적으로 jqLite가 사용됩니다. 인수는 내부적으로 ID로 이해되며 해당 jQuery 오브젝트가 리턴됩니다.


Angular 1.5.8로 지금 시도했습니다. 일반 ID는 빈 결과를 반환합니다. angular.element("#myId")잘 작동합니다.
Gosha U.

어쩌면 페이지에 jQuery가 있습니까?
Vishal Anand
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.