angular.element vs document.getElementById या jQuery चयनकर्ता स्पिन (व्यस्त) नियंत्रण के साथ


157

मैं यहाँ स्पिन के नियंत्रण के "Angularised" संस्करण का उपयोग कर रहा हूँ, जैसा कि यहाँ प्रलेखित है: http://blog.xvitcoder.com/adding-a-weel-progress-indicator-to-your-angularjs-application/

दिखाए गए समाधान के बारे में मुझे जो चीजें पसंद नहीं हैं उनमें से एक है सेवा में jQuery का उपयोग जो प्रभावी रूप से DOM तत्व को स्पिन नियंत्रण प्रदान करता है। मैं तत्व तक पहुंचने के लिए कोणीय निर्माण का उपयोग करना पसंद करूंगा। मैं उस तत्व की आईडी "हार्ड-कोडिंग" से बचना चाहूंगा जिसे स्पिनर को सेवा के भीतर संलग्न करना है और इसके बजाय एक निर्देश का उपयोग करना है जो सेवा (आईडी) में आईडी सेट करता है ताकि सेवा के अन्य उपयोगकर्ता या सेवा को स्वयं यह जानने की आवश्यकता नहीं है।

मैं इस बात से जूझ रहा हूं कि हमें angular.element क्या देता है। एक ही तत्व आईडी पर हमें क्या 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')नहीं

क्या कोई मुझे दस्तावेज़ीकरण के एक अच्छे उदाहरण की ओर इंगित कर सकता है जो कि DOM तत्व बनाम एक कोणीय "तत्व" के उपयोग को स्पष्ट करता है? कोणीय स्पष्ट रूप से अपने गुणों, विधियों आदि के साथ तत्व को "लपेटता है" लेकिन मूल मूल्य प्राप्त करना अक्सर कठिन होता है। उदाहरण के लिए यदि मेरे पास कोई <input type='number'>फ़ील्ड है और मैं उस मूल सामग्री का उपयोग करना चाहता हूं जो यूआई में दिखाई देने वाली मूल सामग्री तक पहुँचती है, जब उपयोगकर्ता प्रकार "-" (बिना उद्धरण के) मुझे कुछ नहीं मिलता है, संभवतः क्योंकि "प्रकार = संख्या" का अर्थ है कोणीय अस्वीकार कर रहा है इनपुट भले ही यह UI में दिखाई दे रहा है और मैं इसे देखना चाहता हूं ताकि मैं इसके लिए परीक्षण कर सकूं और इसे खाली कर सकूं।

किसी भी संकेत / उत्तर की सराहना की।

धन्यवाद।


5
यदि आप jQuery लोड कर रहे हैं तो angular.element एक jQlite ऑब्जेक्ट या jQuery ऑब्जेक्ट है।
नील

जवाबों:


226

यह इस तरह काम कर सकता है:

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

आप Document.querySelector()देशी जावास्क्रिप्ट कॉल को कॉल में लपेटते angular.element()हैं। इसलिए आपको हमेशा एक jqLite या jQuery ऑब्जेक्ट में तत्व मिलते हैं , जो कि jQueryउपलब्ध / लोड होने पर निर्भर करता है।

इसके लिए आधिकारिक दस्तावेज angular.element:

यदि jQuery उपलब्ध है, angular.elementतो jQueryफ़ंक्शन के लिए एक उपनाम है । JQuery उपलब्ध नहीं है, तो angular.elementप्रतिनिधियों कोणीय रों में निर्मित के सबसेट jQuery, कि तथाकथित "jQuery लाइट" या jqLite

सभी तत्व संदर्भ Angularहमेशा jQuery के साथ लिपटे रहते हैं jqLite( या निर्देश संकलन या लिंक फ़ंक्शन में तत्व तर्क)। वे कभी भी कच्चे DOMसंदर्भ नहीं हैं ।

यदि आप आश्चर्य करते हैं कि क्यों उपयोग करना है document.querySelector(), तो कृपया इस उत्तर को पढ़ें ।


41
किसी भी कारण से एक दस्तावेज़ को प्राथमिकता दी जाएगी ।querySelector ('# ...') केवल document.getElementById () का उपयोग करके?
काटो

4
आप इसे एक कोणीय तत्व पर भी कर सकते हैं: var elDivParent = angular.element (elem [0] .querySelector ('# a-id')) ;, elem एक कोणीय तत्व है। इस तरह से आप एक तत्व के अंदर खोज कर सकते हैं। यूनिट परीक्षणों के लिए उपयोगी।
हटा दें

4
@ काटो इस जवाब में अधिक जानकारी । उम्मीद है की वो मदद करदे।
kaiser

Google मैप्स एपीआई के साथ काम करना, और यह काम किया var autocomplete = new google.maps.places.Autocomplete( $document[0].querySelector('#address'), { types: ['geocode'], componentRestrictions: {country: 'us'} } );:। टिप @kaiser के लिए धन्यवाद। किसी कारण से, मैप्स एपी ने शिकायत की कि मैं पहले पैराम में जो कुछ भी पारित किया था वह एक इनपुट नहीं था जब मैंने उपयोग किया था angular.element(document.querySelector('#address')), लेकिन सभी अच्छी तरह से समाप्त हो गए।
निमो

49

यदि आप अभी तक नहीं हैं, तो आपको कोणीय तत्व डॉक्स को पढ़ना चाहिए , ताकि आप समझ सकें कि jqLite द्वारा समर्थित क्या है और क्या नहीं -jqlite कोणीय में निर्मित jquery का सबसेट है।

उन चयनकर्ताओं अकेले jqLite के साथ काम नहीं करेंगे , क्योंकि आईडी द्वारा चयनकर्ताओं का समर्थन नहीं किया जाता है।

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

तो, या तो:

  • आप अकेले jqLite का उपयोग करते हैं, jquery से अधिक सीमित है, लेकिन अधिकांश स्थितियों में पर्याप्त है।
  • या आप अपने ऐप में पूर्ण jQuery के काम को शामिल करते हैं, और इसे सामान्य jquery की तरह उपयोग करते हैं, उन जगहों पर जहां आपको वास्तव में jquery की आवश्यकता होती है।

संपादित करें: ध्यान दें कि jQuery पर पूर्वता लेने के लिए jular को angularJS से पहले लोड किया जाना चाहिए :

वास्तविक jQuery हमेशा jqLite पर पूर्वता लेता है, बशर्ते कि यह DOMContentLoaded घटना से पहले लोड किया गया था।

Edit2: मैंने पहले प्रश्न का दूसरा भाग याद किया:

इस मुद्दे के साथ <input type="number">, मुझे लगता है कि यह एक कोणीय मुद्दा नहीं है, यह मूल html5 संख्या तत्व का इच्छित व्यवहार है ।

यहां तक ​​कि अगर आप इसे jquery के .val()साथ या कच्चे .valueविशेषता के साथ पुनर्प्राप्त करने का प्रयास करते हैं तो यह एक गैर-संख्यात्मक मान नहीं लौटाएगा ।


2
हमारे पास पूरा jQuery लाइब्रेरी है - अन्यथा मेरे $ परिदृश्य को ऊपर बताया गया काम नहीं करेगा। मेरा सवाल था कि $ काम क्यों करता है लेकिन कोणीय.सेलेमेंट नहीं है - भले ही पूर्ण jQuery उपलब्ध हो।
इरिशियन

1
क्या आप angular.js से पहले या बाद में jQuery सहित हैं? इसे कोणीय से पहले शामिल किया जाना चाहिए । आईडी के आधार पर चयनकर्ताओं करना : के साथ jQuery उपलब्ध काम jsbin.com/ohumiy/1/edit
Garst

1
वे एक अन्य निर्देशन में काम कर रहे हैं (यानी आईडी द्वारा कुछ का उपयोग करने के लिए कोणीय)। समस्या उसी तरह से प्रतीत होती है जिस तरह से यह नियंत्रण उस तत्व के साथ जुड़कर काम करता है, हालांकि मुझे समझ नहीं आता कि समान jQuery के बराबर सीधे काम क्यों करना चाहिए। सीधे मेरे निर्देशन का उपयोग करते हुए jQuery का एक समापन टैग है - स्व-समापन टैग काम नहीं करता है (कोई त्रुटि नहीं बस एक रिक्त स्क्रीन) जो मुझे नियंत्रण पर संदेह करता है।
irascian

2
मेरे दूसरे बिंदु पर भी $ मूल्य देखने जैसा कुछ है जिसका उपयोग किसी तत्व की सामग्री को पुनः प्राप्त करने के लिए किया जा सकता है लेकिन इनपुट प्रकार = संख्या के मामले में जहां उपयोगकर्ता के पास इनपुट है - "" यह खाली है। मैं चाहता हूँ कि तत्व पर $ कच्चेइनप्यूटलव्यू जैसी कोई संपत्ति दिखाई दे, क्योंकि बीफोर एंगुलर की सामग्री को देखने के लिए कदम बढ़ाए गए हैं क्योंकि "-" अभी भी यूआई में है, भले ही मेरे पास मेरे निर्देशन में प्रोग्राम के लिए पहुंच नहीं है।
irascian

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

के बराबर है

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

1
यह सुनिश्चित करने के लिए कि आपके निर्भरताएं स्पष्ट हैं और उनका मजाक उड़ाया जा सकता है, का उपयोग करना बेहतर है?
ल्यूक

यह होना चाहिए, लेकिन मुझे लगता है कि कोणीय 2+ में हम सिर्फ टाइपस्क्रिप्ट सुविधाओं पर अधिक भरोसा करते हैं। अब इन चीजों के बारे में चिंता करने की ज़रूरत नहीं है :)
दासुन

17

मुझे नहीं लगता कि यह कोणीय का उपयोग करने का सही तरीका है। यदि कोई फ्रेमवर्क विधि मौजूद नहीं है, तो इसे न बनाएं! इसका मतलब यह है कि यहाँ रूपरेखा (कोणीय) काम नहीं करती है।

कोणीय के साथ आपको इस तरह (jquery तरीके) डोम को हेरफेर नहीं करना चाहिए, लेकिन कोणीय सहायक का उपयोग करें

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

या उस पर पूर्ण नियंत्रण रखने के लिए अपना स्वयं का निर्देश (अपना स्वयं का DOM घटक) बनाएं।

BTW, आप यहाँ देख सकते हैं http://caniuse.com/#search=queryselector querySelector अच्छी तरह से समर्थित है और इसलिए इसे सुरक्षित रूप से उपयोग किया जा सकता है।


2
आप बिल्कुल सही कह रहे है। 90% + मामलों में जो मुझे लगा कि मुझे मैन्युअल रूप से DOM को हेरफेर करने की आवश्यकता है, मैंने जरूरत को दूर करने के लिए कोड को फिर से भरना शुरू किया और अंत में कोड बहुत अधिक क्लीनर है।
स्टीफन चुंग

17

यदि कोई व्यक्ति gulp का उपयोग करता है, तो यदि हम उपयोग करते हैं तो यह एक त्रुटि दिखाता है document.getElementById()और यह उपयोग करने का सुझाव देता है $document.getElementById()लेकिन यह काम नहीं करता है।

उपयोग -

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

कोणीय एक सरणी यहाँ क्यों इंजेक्शन है?
पीटर

16

आप $ दस्तावेज़ का उपयोग करके तत्वों तक पहुँच सकते हैं ($ दस्तावेज़ को इंजेक्ट करने की आवश्यकता है)

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
खोज () - टैग नाम से लुकअप तक सीमित
RJV

angular.element (दस्तावेज़) .find ( 'SomeClass।'); पूरी तरह से ठीक काम करता है।
निशांत बरनवाल

10

आपको अपने नियंत्रक में $ दस्तावेज़ को इंजेक्ट करना चाहिए, और मूल दस्तावेज़ ऑब्जेक्ट के बजाय इसका उपयोग करना चाहिए।

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

यदि आपको jquery स्टाइल एलिमेंट रैप की आवश्यकता नहीं है, तो $ डॉक्यूमेंट [0] .querySelector ('# MyID') आपको DOM ऑब्जेक्ट देगा।


1
आप Angulars $ डॉक्युमेंट सर्विस ओवरहेड का उपयोग करने के बजाय सीधे window.document का संदर्भ ले सकते हैं।
MatBee

5
बेशक आप अगर आप अपने सबसे बेकार में $ दस्तावेज़ का मजाक उड़ाने के बारे में चिंता नहीं करते हैं
Adamy

मेरे लिए स्पष्ट नहीं है: मुझे यह वार्निग मिलता है: आपको डिफ़ॉल्ट दस्तावेज़ ऑब्जेक्ट के बजाय $ दस्तावेज़ सेवा का उपयोग करना चाहिए, लेकिन इसका क्या मतलब है? इसके बारे में कोई डॉक्स? धन्यवाद!
असली नोट

@ असली आप अपनी जावास्क्रिप्ट में कहीं से भी HTML डोम डॉक्यूमेंट ऑब्जेक्ट एक्सेस कर सकते हैं। 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
तत्व अपरिभाषित है? jQuery के बिना तुम्हारा प्रयास करने के लिए angular.element.find मेरे लिए कोई फ़ंक्शन नहीं है।
उतरा

3
कृपया ऐसा न करें। अन्य उदाहरणों में से एक का उपयोग करें। यह कोई हैश तालिका लुकअप अनुकूलन का उपयोग करता है।
19

4

केसर के उत्तर में सुधार:

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

$documentअपने निर्देश में इंजेक्ट करना मत भूलना


21
जैसा कि element.find के लिए कोणीय प्रलेखन में उल्लेख किया गया है : find() - Limited to lookups by tag nameयह आईडी पर काम नहीं करता है। इसके अलावा, आपके पास एक अतिरिक्त समापन है )
पाट

3

शायद मुझे यहाँ आने में बहुत देर हो गई लेकिन यह काम करेगा:

var target = angular.element(appBusyIndicator);

ध्यान दें, कोई भी नहीं है appBusyIndicator, यह सादे आईडी मूल्य है।

पर्दे के पीछे क्या हो रहा है: (यह मानते हुए कि यह एक div पर लागू होता है) (angular.js लाइन नंबर: 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 का उपयोग किया जाएगा। तर्क को आंतरिक रूप से एक आईडी के रूप में समझा जाता है और इसी jQuery ऑब्जेक्ट को लौटाया जाता है।


मैंने इसे अभी Angular 1.5.8 के साथ आज़माया है। एक सादा आईडी खाली परिणाम देता है। angular.element("#myId")अच्छा काम करता है।
गोशाला उ।

शायद आपके पेज पर jQuery है?
विशाल आनंद
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.