Ajax Konusunda Uzmanlaşma, Bölüm 5

0
butch
IBM Türkiye ve Fazlamesai.net işbirliği ile dilimize kazandırılan yeni bir IBM developerWorks makalesi ile karşınızdayız. Diğer makalelere buradan ulaşabilirsiniz.

Makalenin özgün haline bu adresten ulaşabilirsiniz.

Ajax'ta Uzmanlaşma, Bölüm 5: DOM'nin kullanılması

Web sayfalarınızı hızla güncellemek için JavaScript kullanın

Düzey: Başlangıç

Brett McLaughlin (brett@newInstance.com), Yazar ve Editör, O'Reilly Media Inc.

11 Nisan 2006

Geçen ay Brett, öğeleri sahne arkasında Web sayfalarınızı tanımlamak için çalışan Belge Nesne Modeli'ni tanıtmıştı. Bu ay, DOM ile ilgili daha derin konulara giriyor. DOM ağacının paçalarını nasıl yaratabileceğinizi, kaldırabileceğinizi ve değiştirebileceğinizi öğrenin ve Web sayfalarınızı hızla güncellemek için sonraki adımı atın!
 

Bu dizide geçen ay yayınlanan yazımı okuduysanız, bir Web tarayıcısı Web sayfalarınızdan birini görüntülediğinde neler olup bittiğini birinci elden öğrenmişsinizdir. O yazımda da anlattığım gibi, sayfanız için tanımladığınız HTML ve CSS bir Web tarayıcısına gönderildiğinde, metinden bir nesne modeline çevrilir. Kodun basit ya da karmaşık olmasından, tümünün bir dosyada ya da ayrı dosyalarda saklanmasından bağımsız olarak bu geçerlidir. Daha sonra tarayıcı, sağladığınız metin dosyalarıyla çalışmak yerine, doğrudan nesne modeliyle çalışır. Tarayıcının kullandığı modele Belge Nesne Modeli denir. Belgelerinizdeki öğeleri, öznitelikleri ve metni temsil eden nesneleri bir birine bağlar. HTML ve CSS içindeki tüm stiller, değerler ve hatta boşlukların çoğu nesne modelinde birleştirilir. Belirli bir Web sayfasına ilişkin özel modele, sayfanın DOM ağacı denir.

Bir DOM ağacının ne olduğunu anlamak ve HTML'nizi ve CSS'nizi nasıl gösterdiğini bilmek, Web sayfalarınızın denetimini almak konusunda atacağınız ilk adımdır. Daha sonra, belirli bir Web sayfası için DOM ağacıyla nasıl çalışacağınızı öğrenmeniz gerekir. Örneğin, DOM ağacına bir öğe eklerseniz, bu öğe hemen kullanıcının Web tarayıcısında görüntülenir -- sayfanın yeniden yüklenmesine gerek yoktur. DOM ağacından metnin bir kısmını kaldırdığınızda da metin, kullanıcının ekranından kaybolur. Kullanıcı arabirimini DOM aracılığıyla değiştirebilir ve kullanıcı arabirimiyle DOM üzerinden etkileşime geçebilirsiniz; bu da size programlama konusunda inanılmaz bir güç ve esneklik sağlar. DOM ağacıyla nasıl çalışılacağını öğrendiğinizde, zengin içerikli, etkileşimli, dinamik Web sitelerine doğru büyük bir adım atarsınız.

Aşağıdaki konular geçen ayki "Web yanıtı için DOM'yi kullanma" yazısını temel alır; o makaleyi henüz okumadıysanız, buradan ileri gitmeden önce okumak isteyebilirsiniz.

Kısaltmalarda telaffuz önemlidir

Birçok açıdan Belge Nesne Modeli'ne, çok daha kolay bir şekilde Belge Düğüm Modeli denilebilirdi. Elbette, insanların çoğu düğüm teriminin anlamını bilmediği ve "DNM"nin, "DOM" kadar kolay söylenemediği için W3C'nin neden DOM kısaltmasını seçtiğini anlamak çok da zor değil.

Çeşitli tarayıcılar ve dillerle kullanılabilir

Belge Nesne Modeli, bir W3C standardıdır (W3C bağlantıları için Kaynaklar bölümüne bakın). Bu nedenle, tüm modern Web tarayıcıları DOM'yi, en azından belirli bir düzeye kadar destekler. Tarayıcılar arasında bazı farklılıklar vardır, ancak temel DOM işlevselliğini kullanırsanız -- ve birkaç özel ve olağandışı duruma dikkat ederseniz -- DOM kodunuz tüm tarayıcılarda aynı şekilde çalışacaktır. Opera içindeki bir Web sayfasını değiştirmek için yazdığınız kod, Apple's Safari®, Firefox®, Microsoft® Internet Explorer® ve Mozilla® tarayıcılarında da çalışır.

DOM'yi aynı zamanda yaygın olarak kullanılan programlama dillerinin çoğuyla birlikte kullanabilirsiniz. W3C, DOM için birkaç dil ilişkilendirmesi tanımlamıştır. Dil ilişkilendirmesi, basit anlamda, DOM'yi belirli bir dille kullanabilmeniz için tanımlanan bir API'dir. Örneğin, C, Java ve JavaScript için iyi tanımlanmış DOM dil ilişkilendirmeleri bulabilirsiniz. Dolayısıyla, DOM'yi bu dillerin herhangi biriyle kullanabilirsiniz. Dil ilişkilendirmeleri, diğer bazı diller için de mevcuttur, ancak bunların çoğu W3C tarafından değil, üçüncü taraflar tarafından tanımlanmıştır.

Bu dizide, DOM ile JavaScript ilişkilendirmeleri konusuna odaklanacağım. Çoğu zamanuyumsuz uygulama geliştirme Web tarayıcısında çalıştırılmak üzere JavaScript kodunda yazıldığı için bu oldukça anlamlıdır. JavaScript ve DOM ile kullanıcı arabirimini hızla değiştirebilir, kullanıcı olaylarına ve girişlerine yanıt verebilir ve daha birçok işlem yapabilirsiniz -- tüm bunları oldukça standartlaşmış JavaScript'i kullanarak gerçekleştirirsiniz.

Tüm bunlar söylendikten sonra, diğer dillerdeki DOM dil ilişkilendirmelerine debakmanızı öneririm. Örneğin, Java dili ilişkilendirmelerini yalnızca HTML ile değil, aynı zamanda bu makalenin sonraki kısımlarında da anlatacağım gibi, XML ile de çalışmak için kullanabilirsiniz. Burada öğreneceğiniz dersler HTML'in ötesinde, yalnızca istemci tarafı JavaScript'inden çok daha fazla ortam için geçerlidir.


Kavramsal düğüm

Düğüm, DOM içindeki en temel nesne tipidir. Aslında, bu makalenin sonraki kısımlarında da göreceğiniz gibi, DOM ile tanımlanan neredeyse her nesne düğüm nesnesini genişletir. Ancak, semantikle ilgili daha ileri aşamalara geçmeden önce, bir düğümün temsil ettiği kavramı anlamanız gerekir; daha sonra, düğümün gerçek özelliklerini ve yöntemlerini öğrenmek sizin için çok kolay olacaktır.

Bir DOM ağacında, karşılaşacağınız hemen hemen her şey bir düğümdür. DOM ağacındaki her öğe, en temel düzeyinde bir düğümdür. Her öznitelik bir düğümdür. Her metin parçası bir düğümdür. Açıklamalar, özel karakterler (telif hakkı simgesini temsil eden © gibi) ve DOCTYPE bildirimi (HTML ya da XHTML'nizde varsa) bile birer düğümdür. Bu tiplerin ayrı ayrı özelliklerine girmeden önce, düğümün ne anlama geldiğini gerçekten kavramanız gerekir.

Düğüm bir...

En basit anlatımla düğüm, bir DOM ağacındaki tek bir şeydir. "Şey" sözcüğü, belirsizliği nedeniyle özellikle kullanılmıştır, çünkü bu olabilecek en belirgin terimdir. Örneğin, HTML'nizdeki bir öğe (img gibi) ile HTML'nizdeki bir metin parçasının ("Scroll down for more details" gibi) birçok ortak özelliğe sahip oldukları yeterince açık olmayabilir. Ancak bunun nedeni, bu ayrı tiplere işlevleri açısından bakmanız ve birbirlerinden ne kadar farklı olduklarını düşünmenizdir.

Bunun yerine, DOM ağacındaki her bir öğenin ve metin parçasının bir üst öğesinin olduğunu; bu üst öğenin de, başka bir öğenin alt öğesi (img öğesinin p öğesine yerleştirilmesi gibi) ya da DOM ağacındaki en üst öğe olduğunu (her belge için bir defalık özel bir durumdur ve html öğesini kullandığınız yerdir) düşünün. Ayrıca, hem öğelerin hem de metnin bir tipinin olduğunu dikkate alın. Bir öğeye ilişkin tip, gayet açık olarak öğedir; metne ilişkin tip de metindir. Her bir düğümün oldukça iyi tanımlanmış bir yapısı da vardır: kendi altında, alt öğeler gibi düğümleri var mı? Kardeş düğümleri (öğe ya da metnin "yanındaki" düğümler) var mı? Her bir düğüm hangi belgeye ait?

Açıkçası, bunların çoğu oldukça soyut görünür. Aslında, bir öğe tipinin öğe olduğunu söylemek biraz saçma görünebilir. Ancak, ortak bir nesne tipi olarak düğümün sahip olduğu değeri anlamanız için biraz soyut düşünmeniz gerekir.

Ortak düğüm tipi

DOM kodunuzun içinde en çok gerçekleştireceğiniz tek görev bir sayfanın DOM ağacında gezinmek olacaktır. Örneğin, "id" özniteliğine göre bir formu bulabilir ve bu formun içindeki iç içe geçmiş öğelerle ve metinle çalışmaya başlayabilirsiniz. Metin yönergeleri, giriş alanlarına ilişkin etiketler, gerçek inputöğeleri ve büyük olasılıkla diğer HTML öğeleri (img öğeleri gibi) ve bağlantılar (a öğeleri) olacaktır. Öğeler ve metin tamamen farklı tiplerdeyse, bir tipten diğerine geçmek için tamamen farklı kod parçaları yazmanız gerekir.

Bir ortak düğüm tipi kullanırsanız her şey farklılaşır. Böyle bir durumda, basit bir şekilde düğümden düğüme geçer ve düğümün tipiyle, yalnızca bir öğe ya da metinle ilgili özel bir şey yapmak istediğinizde ilgilenirsiniz. DOM ağacında dolaşırken, bir öğenin üst öğesine -- ya da alt öğelerine -- geçmek için, diğer düğüm tiplerinde gerçekleştireceğiniz işlemleri kullanırsınız. Bir düğüm tipiyle, yalnızca belirli bir düğüm tipine özgü (öğenin öznitelikleri gibi) bir şeyler yapmanız gerektiğinde özel olarak çalışmanız gerekir. DOM ağacındaki her bir nesneyi bir düğüm olarak düşünmek, çalışmanızı çok basitleştirir. Aklınızdan bunu çıkarmadan, bir sonraki bölümde, özellikler ve yöntemlerden başlayarak DOM Düğüm yapısının tam olarak neler sunduğuna bakacağım.


Düğüm özellikleri

DOM düğümleriyle çalışırken bazı özellikleri ve yöntemleri kullanmak isteyeceksiniz; o zaman önce bunları gözden geçirelim. Bir DOM düğümünün temel özellikleri şunlardır:

  • nodeName, düğümün adını bildirir (ek bilgi için aşağıya bakın).
  • nodeValue, düğümün "değerini" verir (ek bilgi için aşağıya bakın).
  • parentNode, düğümün üst öğesini verir. Her öğenin, özniteliğin ve metnin bir üst öğesinin olduğunu unutmayın.
  • childNodes, bir düğümün alt öğelerinin listesidir. HTML ile çalışırken, bu liste yalnızca bir öğe üzerinde çalışırken işe yarar; metin düğümlerinin ve öznitelik düğümlerinin alt düğümleri yoktur.
  • firstChild, childNodes listesindeki birinci düğüme giden bir kısayoldur.
  • lastChild, childNodes listesindeki son düğüme giden bir kısayoldur.
  • previousSibling, geçerli düğümden önceki düğümü verir. Diğer bir deyişle, bu düğümün üst öğesinin childNodes listesinde, geçerli düğümden bir önceki düğümü verir (kafanız karıştıysa, son cümleyi yeniden okuyun).
  • nextSibling, previousSibling özelliğine benzer; üst öğenin childNodes listesindeki bir sonraki düğümü verir.
  • attributes, yalnızca bir öğe düğümünde yararlı olur; bir öğenin özniteliklerinin listesini verir.

Diğer birkaç özellik, daha soysal XML belgeleri için geçerlidir ve HTML tabanlı Web sayfalarıyla çalıştığınızda pek de işinize yaramazlar.

Alışılmadık özellikler

nodeName ve nodeValue özelliklerinin dışında, yukarıda tanımlanan özelliklerin çoğu kendi kendini anlatmaktadır. Bu özellikleri yalnızca açıklamak yerine birkaç garip soruyu düşünün: Bir metin düğümü için nodeName (düğümAdı) değeri ne olurdu? Benzer bir şekilde, Bir öğeye ilişkin nodeValue (düğümDeğeri) ne olurdu?

Bu sorular sizi şaşırttıysa, bu özelliklerin doğasında varolan karışıklık olasılığını da anlamışsınızdır. nodeName ve nodeValue, gerçekte tüm düğüm tipleri için geçerli değildir (bu, bir düğümdeki diğer özelliklerin birkaçı için de geçerlidir). Bu, bir anahtar kavramı da şekillendirir: Bu değerlerin herhangi biri boş bir değer verebilir (bazen JavaScript içinde "undefined" [tanımlanmamış] olarak görünür). Örneğin, bir metin düğümüne ilişkin nodeName özelliği boş bir değerdir (ya da bazı tarayıcılarda metin düğümlerinin bir adı olmadığı için "undefined" [tanımlanmamış] olur). nodeValue, bekleyeceğiniz üzere düğümün metnini döndürür.

Benzer şekilde, öğelerin bir nodeName özelliği vardır (öğenin adı), ancak bir öğe nodeValue özelliğinin değeri her zaman boştur. Özniteliklerin, hem nodeName hem de nodeValue özellikleri için değerleri vardır. Bir sonraki bölümde bu ayrı tiplerle ilgili biraz daha ayrıntıya gireceğim, ancak bu özellikler her düğümün parçası olduğu için, burada bunlardan söz etmekte fayda var.

Şimdi, çalışan düğüm özelliklerinin birkaçını gösteren Liste 1'e bakın.



Liste 1. DOM içinde düğüm özelliklerinin kullanılması
    // These first two lines get the DOM tree for the current Web page, 
    //   and then the <html> element for that DOM tree
    var myDocument = document;
    var htmlElement = myDocument.documentElement;

    // What's the name of the <html> element? "html"
    alert("The root element of the page is " + htmlElement.nodeName);

    // Look for the <head> element
    var headElement = htmlElement.getElementsByTagName("head")[0];
    if (headElement != null) {
      alert("We found the head element, named " + headElement.nodeName);
      // Print out the title of the page
      var titleElement = headElement.getElementsByTagName("title")[0];
      if (titleElement != null) {
        // The text will be the first child node of the <title> element
        var titleText = titleElement.firstChild;
        // We can get the text of the text node with nodeValue
        alert("The page title is '" + titleText.nodeValue + "'");
      }

      // After <head> is <body>

      var bodyElement = headElement.nextSibling;
      while (bodyElement.nodeName.toLowerCase() != "body") {
        bodyElement = bodyElement.nextSibling;
      }

      // We found the <body> element...

      // We'll do more when we know some methods on the nodes.
    }


Düğüm yöntemleri

Sırada tüm düğümlerle kullanılabilen yöntemler var (düğüm özelliklerinde olduğu gibi, çoğu HTML DOM işlemleri için gerçekten geçerli olmayan birkaç yöntemi atladım):

  • insertBefore(newChild, referenceNode), referenceNode değerinden önce newChild düğümünü yerleştirir. Bu kodu, istediğiniz newChild düğümünün üst öğesinde çağıracağınızı unutmayın.
  • replaceChild(newChild, oldChild), oldChild düğümünü newChild düğümüyle değiştirir.
  • removeChild(oldChild), işlevin çalıştırıldığı düğümden oldChild düğümünü kaldırır.
  • appendChild(newChild), bu işlevin çalıştırıldığı düğüme newChild düğümünü ekler. newChild, hedef düğümün alt öğelerinin sonuna eklenir.
  • hasChildNodes(), çağrıldığı düğümün alt öğeleri varsa doğru, yoksa yanlış değerini döndürür.
  • hasAttributes(), çağrıldığı düğümün öznitelikleri varsa doğru, özniteliği yoksa yanlış değerini döndürür.

Çoğu bölümde, bu yöntemlerin tümünün, büyük ölçüde bir düğümün alt öğeleriyle ilgili olduğunu fark etmişsinizdir. Bu, onların birincil amacıdır. Yalnızca bir metin düğümünün değerini ya da bir öğenin adını kavramaya çalışıyorsanız, basit bir şekilde düğümün özelliklerini kullanabileceğiniz için yöntemleri çok sık çağırmazsınız. Liste 2, yukarıdaki yöntemlerin bazılarını kullanarak Liste 1'deki kod üzerine kurulur.



Liste 2. DOM içinde düğüm yöntemlerinin kullanılması
// These first two lines get the DOM tree for the current Web page, 
    //   and then the <html> element for that DOM tree
    var myDocument = document;
    var htmlElement = myDocument.documentElement;

    // What's the name of the <html> element? "html"
    alert("The root element of the page is " + htmlElement.nodeName);

    // Look for the <head> element
    var headElement = htmlElement.getElementsByTagName("head")[0];
    if (headElement != null) {
      alert("We found the head element, named " + headElement.nodeName);
      // Print out the title of the page
      var titleElement = headElement.getElementsByTagName("title")[0];
      if (titleElement != null) {
        // The text will be the first child node of the <title> element
        var titleText = titleElement.firstChild;
        // We can get the text of the text node with nodeValue
        alert("The page title is '" + titleText.nodeValue + "'");
      }

      // After <head> is <body>

      var bodyElement = headElement.nextSibling;
      while (bodyElement.nodeName.toLowerCase() != "body") {
        bodyElement = bodyElement.nextSibling;
      }

      // We found the <body> element...

      // Remove all the top-level <img> elements in the body
      if (bodyElement.hasChildNodes()) {
        for (i=0; i<bodyElement.childNodes.length; i++) {
          var currentNode = bodyElement.childNodes[i];
          if (currentNode.nodeName.toLowerCase() == "img") {
            bodyElement.removeChild(currentNode);
          }
        }
      }
    }


Beni sına!

Şimdiye kadar Liste 1 ve 2'de yalnızca iki örnek gördünüz, ancak bunlar bile DOM ağacını kullanmaya başladığınızda yapabileceklerinize ilişkin her tür fikri vermiş olmalı. Buraya kadar gösterildiği biçimde kodu denemek isterseniz, Liste 3'ü bir HTML dosyasına aktarın, kaydedin ve Web tarayıcınıza yükleyin.



Liste 3. DOM'nin kullanıldığı bazı JavaScript kodlarının bulunduğu bir HTML dosyası
<html>
 <head>
  <title>JavaScript and the DOM</title>
  <script language="JavaScript">
   function test() {
    // These first two lines get the DOM tree for the current Web page,
    //   and then the <html> element for that DOM tree
    var myDocument = document;
    var htmlElement = myDocument.documentElement;

    // What's the name of the <html> element? "html"
    alert("The root element of the page is " + htmlElement.nodeName);

    // Look for the <head> element
    var headElement = htmlElement.getElementsByTagName("head")[0];
    if (headElement != null) {
      alert("We found the head element, named " + headElement.nodeName);
      // Print out the title of the page
      var titleElement = headElement.getElementsByTagName("title")[0];
      if (titleElement != null) {
        // The text will be the first child node of the <title> element
        var titleText = titleElement.firstChild;
        // We can get the text of the text node with nodeValue
        alert("The page title is '" + titleText.nodeValue + "'");
      }

      // After <head> is <body>

      var bodyElement = headElement.nextSibling;
      while (bodyElement.nodeName.toLowerCase() != "body") {
        bodyElement = bodyElement.nextSibling;
      }

      // We found the <body> element...

      // Remove all the top-level <img> elements in the body
      if (bodyElement.hasChildNodes()) {
        for (i=0; i<bodyElement.childNodes.length; i++) {
          var currentNode = bodyElement.childNodes[i];
          if (currentNode.nodeName.toLowerCase() == "img") {
            bodyElement.removeChild(currentNode);
          }
        }
      }
    }
  }
  </script>
 </head>
 <body>

  <p>JavaScript and DOM are a perfect match. 
     You can read more in <i>Head Rush Ajax</i>.</p>
  <img src="http://www.headfirstlabs.com/Images/hraj_cover-150.jpg" />
  <input type="button" value="Test me!" onClick="test();" />
 </body>

</html>

Bu sayfayı tarayıcınıza yüklediğinizde, Şekil 1'dekine benzer bir sayfa görmeniz gerekir.



Şekil 1. JavaScript çalıştırmak üzere bir düğmesi olan basit bir HTML sayfası
JavaScript çalıştırmak üzere bir düğmesi olan basit bir HTML sayfası

Test me! (Beni sına!) düğmesini tıklattığınızda Şekil 2'deki gibi uyarı kutuları görüntülenmeye başlar.



Şekil 2. nodeValue değeri kullanılarak, bir öğenin adını gösteren uyarı kutuları
nodeValue değeri kullanılarak, bir öğenin adını gösteren uyarı kutuları

Kod çalışmayı tamamladığında, resimler Şekil 3'te gösterildiği gibi gerçek zamanlı olarak sayfadan kaldırılır.



Şekil 3. JavaScript kullanılarak, gerçek zamanlı olarak kaldırılan resimler
JavaScript kullanılarak, gerçek zamanlı olarak kaldırılan resimler

API tasarım notları

Her bir düğümdeki kullanılabilir özelliklere ve yöntemlere yeniden bakın. Bunlar, nesne odaklı (OO) programlama kullananlar için DOM'ye ilişkin bir temel noktayı açıklar: DOM çok da nesne odaklı bir API değildir. Birincisi, birçok durumda bir düğüm nesnesinde yöntem çağırmak yerine, nesnenin özelliklerini doğrudan kullanırsınız. getNodeName() yöntemi yoktur; örneğin, nodeName özelliğini doğrudan kullanırsınız. Dolayısıyla düğüm nesneleri (ve diğer DOM nesneleri), özellikleri aracılığıyla, yalnızca işlevleri değil, birçok veriyi de gösterir.

İkincisi, özellikle Java ya da C++ gibi dillerde aşırı yüklü nesnelerle ve nesne odaklı API'lerle çalışmaya alıştıysanız, DOM içindeki nesnelerin ve yöntemlerin adlandırılması biraz garip görünebilir. DOM'nin, birkaç dil belirtmek gerekirse, C, Java ve JavaScript içinde çalışması gerekir; bu yüzden, API tasarımından bazı ödünler verilmiştir. Örneğin, aşağıdaki gibi görünen NamedNodeMap yöntemlerinde iki farklı yöntem görürsünüz:

  • getNamedItem(String name)
  • getNamedItemNS(Node node)

OO programcıları için bu oldukça garip görünür. İki yöntemin amacı aynıdır, ancak biri bir dizeyi (String) alırken, diğeri bir düğümü (Node) alır. OO API'lerinin çoğunda, her iki sürüm için de aynı yöntem adını kullanırdınız. Kodunuzu çalıştıran sanal makine, yönteme geçirilen nesne tipine dayalı olarak çalıştırılacak yöntemi belirlerdi.

Buradaki sorun, JavaScript'in yöntem aşırı yüklemesi adı verilen bu tekniği desteklememesidir. Diğer bir deyişle, JavaScript belirli bir adda tek bir yöntem ya da işlevin olmasına izin verir. Bir dizeyi alan getNamedItem() adlı bir yönteminiz varsa, ikinci sürüm farklı tipte bir bağımsız değişken (ya da tamamen farklı bir bağımsız değişkenler kümesi) alsa bile getNamedItem() adlı başka bir yönteminiz ya da işleviniz olamaz. Bunu yaparsanız JavaScript bir hata bildirir ve kodunuz, çalışmasını beklediğiniz gibi çalışmaz.

Özünde, DOM bilinçli olarak yöntem aşırı yüklemesinden ve diğer OO programlama tekniklerinden kaçınır. Bunu, API'nin OO programlama tekniklerini desteklemeyenler de dahil olmak üzere birden çok dil üzerinde çalıştığından emin olmak için yapar. Sonuçta fazladan birkaç yöntem adı öğrenmeniz gerekir. İyi tarafı da DOM'yi herhangi bir dilde öğrenebileceğiniz -- Java gibi -- ve aynı yöntem adlarının ve kodlama yapısının DOM uygulaması olan diğer dillerde de -- JavaScript gibi -- çalışacağını bilmektir.

Programcılar dikkat etsin

API tasarımıyla uğraşıyorsanız -- ya da yalnızca yakından ilgileniyorsanız -- bir şeyi merak edebilirsiniz: "Düğüm tipine ilişkin özellikler neden tüm düğümler için ortak değil?" Bu güzel bir sorudur ve yanıtı, teknik nedenlerden çok politika ve karar almayla ilgilidir. Kısacası, yanıt "Kim bilir! Ama bu biraz can sıkıcı, değil mi?" olur.

nodeName özelliği her tipin bir adı olması için tasarlanmıştır; ancak birçok durumda, ad tanımlanmamıştır ya da programcılar için değer taşımayan garip bir iç addır (örneğin, Java'da bir metin düğümünün nodeName özelliği, birçok durumda "#text" olarak bildirilir). Aslında, hata işlemenin size bırakıldığını varsaymanız gerekir. Hemen myNode.nodeName değerine erişmek ve bu değeri kullanmak güvenli değildir; birçok durumda, değer boş olacaktır. Bu yüzden, programlama söz konusu olduğunda bu durumlarda programcıların dikkat etmesi gerekir.


Ortak düğüm tipleri

Bir DOM düğümünün belirleyici niteliklerinin ve özelliklerinin bazılarını (ve bazı garipliklerini) gördüğünüze göre, birlikte çalışacağınız düğümlerin belirli tiplerinden bazılarıyla ilgili bilgileri öğrenmeye hazırsınız demektir. Web uygulamalarının çoğunda, yalnızca dört düğüm tipiyle çalışırsınız:

  • Belge düğümü, tüm HTML belgesini belirtir.
  • Öğe düğümleri, a ya da img gibi HTML öğelerini belirtir.
  • Öznitelik düğümleri, HTML öğelerindeki href (a öğesinde) ya da src (img öğesinde) gibi öznitelikleri gösterir.
  • Metin düğümleri, HTML belgesindeki "Click on the link below for a complete set list" gibi metinleri belirtir. Bu, p, a ya da h2 gibi öğelerin içinde görünen metindir.

HTML ile uğraşırken, zamanınızın yaklaşık %95'ini bu düğüm tipleriyle çalışarak geçirirsiniz. Bu nedenle, bu ayki makalenin geri kalan kısmını bu konuda daha ayrıntılı bilgi vermek için kullanacağım. (İleride yazacağım bir makalede XML konusunu anlatırken, diğer düğüm tiplerinden bazılarını da tanıtacağım.)


Belge düğümü

Birinci düğüm tipi, yazdığınız DOM tabanlı hemen her kodda kullanacağınız belge düğümüdür. Belge düğümü, aslında HTML (ya da XML) sayfasının bir öğesi değil, sayfanın kendisidir. Dolayısıyla HTML Web sayfasında, belge düğümü tüm DOM ağacıdır. JavaScript'te, document anahtar sözcüğünü kullanarak belge düğümüne erişebilirsiniz:

// These first two lines get the DOM tree for the current Web page,
//   and then the <html> element for that DOM tree
var myDocument = document;
var htmlElement = myDocument.documentElement;

JavaScript'teki document anahtar sözcüğü, geçerli Web sayfasına ilişkin DOM ağacını gösterir. Buradan, ağaçtaki tüm düğümlerle çalışabilirsiniz.

Aşağıdaki yöntemlere benzer yöntemleri kullanarak yeni düğümler yaratmak için document belgesini de kullanabilirsiniz:

  • createElement(elementName), sağlanan adla bir öğe oluşturur.
  • createTextNode(text), sağlanan metinle yeni bir metin düğümü oluşturur.
  • createAttribute(attributeName), sağlanan adla yeni bir öznitelik oluşturur.

Dikkat edilmesi gereken temel nokta, bu yöntemlerin düğümleri yarattığı, ancak bunları herhangi bir belirli belgeye bağlamadığı ya da yerleştirmediğidir. Bunun için, insertBefore() ya da appendChild() gibi önceden gördüğünüz yöntemlerden birini kullanmanız gerekir. Aşağıdakine benzer bir kod kullanarak yeni bir öğe oluşturabilir ve bunu, bir belgeye ekleyebilirsiniz:

var pElement = myDocument.createElement("p");
var text = myDocument.createTextNode("Here's some text in a p element.");
pElement.appendChild(text);
bodyElement.appendChild(pElement);

Bir Web sayfasının DOM ağacına erişmek için document öğesini kullandıktan sonra, öğelerle, özniteliklerle ve metinle doğrudan çalışmaya başlayabilirsiniz.


Öğe düğümleri

Öğe düğümleriyle çok çalışacaksınız, ancak öğeler üzerinde gerçekleştirmeniz gereken birçok işlem, yalnızca öğelere özel yöntemler ve özellikler yerine, tüm düğümler için geçerli yöntemleri ve özellikleri içerir. Yalnızca iki yöntem takımı öğelere özeldir:

  1. Özniteliklerle çalışmaya ilişkin yöntemler:
    • getAttribute(name), name adlı özniteliğin değerini döndürür.
    • removeAttribute(name), name adlı özniteliği kaldırır.
    • setAttribute(name, value), name adlı bir öznitelik oluşturur ve değerini value değerine ayarlar.
    • getAttributeNode(name), name adlı öznitelik düğümünü verir (öznitelik düğümleri aşağıda ele alınmıştır).
    • removeAttributeNode(node), sağlanan düğümle eşleşen öznitelik düğümünü kaldırır.
  2. İç içe geçmiş öğeleri bulmaya ilişkin yöntemler:
    • getElementsByTagName(elementName), sağlanan adın bulunduğu öğe düğümleri listesini verir.

Bunların tümü büyük ölçüde kendi kendilerini açıklar niteliktedir, ancak yine de aşağıdaki örneklere bakmanızda yarar vardır.

Özniteliklerle çalışma

Özniteliklerle çalışmak oldukça kolaydır; örneğin, document nesnesiyle ve öğesiyle ve yukarıdaki yöntemlerin bazılarıyla yeni bir img öğesi oluşturabilirsiniz:

var imgElement = document.createElement("img");
imgElement.setAttribute("src", "http://www.headfirstlabs.com/Images/hraj_cover-150.jpg");
imgElement.setAttribute("width", "130");
imgElement.setAttribute("height", "150");
bodyElement.appendChild(imgElement);

Bu, şimdiye kadar oldukça rutin görünmüş olabilir. Aslında, bir düğüm kavramını anlamaya başladıktan ve kullanılabilir yöntemleri bildikten sonra Web sayfalarınızda ve JavaScript kodunuzda DOM ile çalışmanın basit olduğunu görmeye başlamanız gerekir. Yukarıdaki kodda, JavaScript yeni bir img öğesi oluşturur, bazı öznitelikleri ayarlar ve bunu daha sonra HTML sayfasının gövdesine ekler.

İç içe geçmiş öğelerin bulunması

İç içe geçmiş öğeleri bulmak da kolaydır. Örneğin, Liste 3'teki HTML sayfasında bulunan tüm img öğelerini bulmak ve kaldırmak için aşağıdaki kodu kullandım:

      // Remove all the top-level <img> elements in the body
      if (bodyElement.hasChildNodes()) {
        for (i=0; i<bodyElement.childNodes.length; i++) {
          var currentNode = bodyElement.childNodes[i];
          if (currentNode.nodeName.toLowerCase() == "img") {
            bodyElement.removeChild(currentNode);
          }
        }
      }


getElementsByTagName() yöntemini kullanarak da benzer bir etki elde edebilirdiniz:

// Remove all the top-level <img> elements in the body
      var imgElements = bodyElement.getElementsByTagName("img");

      for (i=0; i<imgElements.length; i++) {
        var imgElement = imgElements.item[i];
        bodyElement.removeChild(imgElement);
      }


Öznitelik düğümleri

DOM, öznitelikleri düğüm olarak gösterir ve bir öğenin attributes özelliğini kullanarak her zaman bir öğenin özniteliklerini aşağıda gösterildiği gibi alabilirsiniz:

// Remove all the top-level <img> elements in the body
      var imgElements = bodyElement.getElementsByTagName("img");

      for (i=0; i<imgElements.length; i++) {
        var imgElement = imgElements.item[i];

        // Print out some information about this element
        var msg = "Found an img element!";
        var atts = imgElement.attributes;
        for (j=0; j<atts.length; j++) {
          var att = atts.item(j);
          msg = msg + "\n  " + att.nodeName + ": '" + att.nodeValue + "'";
        }
        alert(msg);

        bodyElement.removeChild(imgElement);
      }

Özniteliklerin garip durumu

DOM söz konusu olduğunda, özniteliklerin biraz özel bir durumu vardır. Bir yandan, öznitelikler diğer öğeler ya da metinler gibi, gerçekte öğelerin alt öğeleri değildir; diğer bir deyişle bir öğenin "altında" görünmezler. Aynı zamanda, bir öğeyle kesinlikle bir ilişkileri vardır; bir öğe özniteliklere "sahiptir". DOM, öznitelikleri göstermek için düğümleri kullanır ve bunları özel bir listeyle bir öğe üzerinde kullanımına sunar. Bu nedenle, öznitelikler DOM ağacının bir parçasıdır, ancak genellikle ağaçta görünmezler. Özniteliklerin, DOM ağacı yapısının geri kalanıyla olan ilişkisinin biraz belirsiz olduğunu söylemek yeterlidir.

attributes özelliğinin aslında düğüm tipi üzerinde olduğunu ve özellikle öğe tipi üzerinde olmadığını belirtelim. Bu biraz gariptir ve kodlamanızı etkilemez, ancak bilinmesi yararlıdır.

Öznitelik düğümleriyle çalışmak kesinlikle mümkündür, ancak özniteliklerle çalışmak için öğede bulunan yöntemlerin kullanılması genellikle daha kolay olur. Yöntemler aşağıdaki gibidir:

  • getAttribute(name), name adlı özniteliğin değerini döndürür.
  • removeAttribute(name), name adlı özniteliği kaldırır.
  • setAttribute(name, value), name adlı bir öznitelik oluşturur ve değerini value değerine ayarlar.

Bu üç yöntem, öznitelik düğümleriyle doğrudan çalışmayı gerektirmez. Bunun yerine, öznitelikleri ve değerlerini yalnızca basit dize özellikleriyle ayarlayabilir ve kaldırabilirsiniz.


Metin düğümleri

Düşünmeniz gereken son düğüm tipi -- en azından HTML DOM ağaçlarıyla çalışırken -- metin düğümleridir. Metin düğümleriyle çalışmak için yaygın olarak kullanacağınız özelliklerin neredeyse tümü, gerçekte düğüm nesnesinde bulunur. Aslında, aşağıda gösterildiği gibi metin düğümünden metin almak için genellikle nodeValue özelliğini kullanacaksınız:

var pElements = bodyElement.getElementsByTagName("p");
for (i=0; i<pElements.length; i++) {
  var pElement = pElements.item(i);
  var text = pElement.firstChild.nodeValue;
  alert(text);
}

Diğer birkaç yöntem, metin düğümlerine özeldir. Bunlar, bir düğümdeki verilere ekleme yapma ya da verileri bölmeyle uğraşırlar:

  • appendData(text), sağladığınız metni, metin düğümünün var olan metninin sonuna ekler.
  • insertData(position, text), metin düğümünün ortasına veri yerleştirmenizi sağlar. Sağladığınız metni, belirtilen konuma yerleştirir.
  • replaceData(position, length, text), belirtilen konumdan başlayarak, belirtilen uzunlukta karakterleri kaldırır ve yönteme sağladığınız metni kaldırılan metnin yerine yerleştirir.

Hangi düğüm tipi?

Şimdiye kadar gördüklerinizin çoğu, çalıştığınız düğüm tipini bildiğiniz varsayımına dayanır, ancak durum her zaman böyle değildir. Örneğin, bir DOM ağacında geziniyorsanız ve ortak düğüm tipleriyle çalışıyorsanız, bir öğeye ya da metne geçtiğinizi fark etmeyebilirsiniz. Bir p öğesinin tüm alt öğelerini alabilir ve metinle mi, bir b öğesiyle mi, yoksa bir img öğesiyle mi çalıştığınızdan emin olamayabilirsiniz. Böyle durumlarda, bir düğümle çalışmaya başlamadan önce ne tip bir düğümle çalıştığınızı anlamanız gerekecektir.

Neyse ki bunu anlamak oldukça basittir. DOM düğüm tipi, aşağıdakilere benzer birkaç değişmez değeri tanımlar:

  1. Node.ELEMENT_NODE, öğe düğüm tipine ilişkin değişmezdir.
  2. Node.ATTRIBUTE_NODE, öznitelik düğüm tipine ilişkin değişmezdir.
  3. Node.TEXT_NODE, metin düğüm tipine ilişkin değişmezdir.
  4. Node.DOCUMENT_NODE, belge düğüm tipine ilişkin değişmezdir.

Başka birkaç düğüm tipi daha vardır, ancak HTML işlemlerinde, bu dördünün dışındakiler çok seyrek olarak kullanılır. Bu değişmezlerin her birine ilişkin değerlerin DOM belirtiminde tanımlanmasına rağmen ben, bilerek bunları atladım; değerle hiçbir zaman doğrudan çalışmamalısınız, değişmezlerin amacı budur!

nodeType özelliği

Bir düğümü yukarıdaki değişmezlerle karşılaştırmak için nodeType özelliğini dekullanabilirsiniz -- bu özellik DOM düğüm tipinde tanımlanır ve tüm düğümler tarafından kullanılabilir:

var someNode = document.documentElement.firstChild;
if (someNode.nodeType == Node.ELEMENT_NODE) {
  alert("We've found an element node named " + someNode.nodeName);
} else if (someNode.nodeType == Node.TEXT_NODE) {
  alert("It's a text node; the text is " + someNode.nodeValue);
} else if (someNode.nodeType == Node.ATTRIBUTE_NODE) {
  alert("It's an attribute named " + someNode.nodeName 
                        + " with a value of '" + someNode.nodeValue + "'");
}

Bu oldukça basit bir örnektir, ancak asıl nokta da budur: bir düğüm tipinin alınması basittir. Daha zor olan konu, düğümün tipini öğrendikten sonra düğümle ne yapacağınızı bilmektir; ancak düğüm, metin, öznitelik ve öğe tipleri konusunda sağlam bir bilgiyle, DOM programlamasını kendi başınıza üstlenmeye hazırsınız.

Ya da neredeyse hazırsınız diyelim.

Çalışmalar için bir anahtar

nodeType özelliği, düğümlerle çalışmanız için gereken bileti size sağlayacakmış gibi görünüyor -- ne tip bir düğümle çalıştığınızı anlamanıza ve daha sonra, bu düğümle ilgili kodu yazmanıza olanak tanıyor. Buradaki sorun, yukarıda tanımlanan Node değişmezlerinin Internet Explorer üzerinde düzgün çalışmamasıdır. Bu nedenle, Node.ELEMENT_NODE, Node.TEXT_NODE ya da diğer değişmezleri kodunuzda kullanırsanız, Internet Explorer Şekil 4'te gördüğünüze benzer bir hata verir.



Şekil 4. Internet Explorer bir hata bildirir
Internet Explorer Düğüm yapısını desteklemez

Internet Explorer, JavaScript'inizde Node değişmezini her kullanışınızda bu hatayı bildirir. Dünyadaki kullanıcıların büyük çoğunluğu hala Internet Explorer kullandığı için kodunuzda Node.ELEMENT_NODE ya da Node.TEXT_NODE gibi yapıları kullanmaktan kaçınabilirsiniz. Internet Explorer programının gelecek sürümü olan Internet Explorer 7.0'da bu sorunun düzeltilmesi beklense de, Internet Explorer 6.x sürümünün yoğun olarak kullanımdan kalkması birkaç yıl sürebilir. Dolayısıyla Node değişmezini kullanmaktan kaçının; DOM kodunuzun (ve Ajax uygulamalarınızın) tüm ana tarayıcılarda çalışması önemlidir.


Sonuç

En üste ulaşmaya hazır mısınız?

DOM'yi gerçekten anlamaya çalışır ve sonunda bu konuda uzmanlaşırsanız, en üst Web programlama beceri düzeyine erişirsiniz. Web programcılarının çoğu kayan resimler yazmak ya da bir formdan değerleri almak için JavaScript'i nasıl kullanacağını bilir; hatta bazıları, sunucuya istek göndermeyi ve sunucudan nasıl yanıt alınacağını da bilir (bu dizinin ilk birkaç makalesinden sonra sizin de bunu yapıyor olmanız gerekir). Ancak, bir Web sayfasının yapısını hızla değiştirmek cesaretsiz ya da deneyimsiz programcılara göre değildir.

Bu dizinin son birkaç makalesinde birçok şey öğrendiniz. Bu noktada, oturup bir sonraki makalede DOM ağacının tüm akıllı kullanım çeşitlerini ele almamı beklememelisiniz. Şimdiki ev ödeviniz DOM ile hoş etkileri ya da parlak arabirimleri nasıl yaratacağınızı keşfetmek. Bu son iki makalede öğrendiklerinizi gözden geçirin ve deney yapıp kodlarla biraz oynamaya başlayın. Bir masaüstü uygulamasını andıran, bir kullanıcı işlemine yanıt olarak nesnelerin ekranda hareket ettiği bir Web sitesi oluşturup oluşturamayacağınızı görün.

Daha da iyisi, ekrandaki her nesnenin çevresine bir sınır çizin ve nesnelerin DOM ağacındaki yerlerini görün ve nesneleri hareket ettirmeye başlayın. Düğümler oluşturun ve bunları var olan alt öğe listelerine ekleyin; iç içe geçmiş birçok düğümden oluşan düğümleri kaldırın; bir düğümün CSS stilini değiştirin ve bu değişikliklerin alt düğümler tarafından alınıp alınmadıklarına bakın. Olasılıklar sınırsızdır ve yeni bir şeyi her deneyişinizde yeni bir şey öğrenirsiniz. Web sayfalarınızla oynamanın tadını çıkarın.

Daha sonra, DOM'ye özel bu üçlemenin son parçasında DOM'nin bazı havalı ve ilginç uygulamalarını programlamanızla nasıl birleştireceğinizi göstereceğim. Kavramsal olarak konuşmayı ve API'yi anlatmayı bırakıp size biraz kod göstereceğim. O zamana kadar, kendinize ait birkaç parlak fikir bulun ve kendi başınıza nelergerçekleştirebileceğinizi görün.


Kaynaklar

Bilgi Edinme
  • Ajax'a giriş konusunda yayınlanan developerWorks serisinin önceki makalelerine bakın:
    • "Introduction to Ajax: Understanding Ajax, a productive approach to building Web sites, and how it works:" (Ajax'a Giriş: Web siteleri oluşturmak için kullanılan verimli bir yaklaşım olarak Ajax'ı ve nasıl çalıştığını anlama ) başlıklı Bölüm 1'de, Ajax bileşen teknolojilerinin birlikte nasıl çalıştığı gösterilmekte ve XMLHttpRequest nesnesinin de içinde bulunduğu Ajax'ın merkezi kavramları ortaya çıkarılmaktadır (Aralık 2005).
    • "Make asynchronous requests with JavaScript and Ajax: Use XMLHttpRequest for Web requests:" (JavaScript ve Ajax ile zamanuyumsuz istekler oluşturma: Web istekleri için XMLHttpRequest kullanma) başlıklı Bölüm 2'de, tarayıcılar arasında XMLHttpRequest örneklerinin nasıl yaratılacağı, isteklerin oluşturulması ve gönderilmesi ve sunucuya yanıt verilmesi gösterilmektedir (Ocak 2006).
    • "Advanced requests and responses in Ajax:" (Ajax'ta gelişmiş istekler ve yanıtlar) başlıklı Bölüm 3'te, standart Web formlarının Ajax ile çalışması ve HTTP durum kodlarıyla, hazır olma durumlarıyla ve XMLHttpRequest nesnesiyle ilgili bilgilerinizi nasıl artırabileceğiniz gösterilmektedir (Şubat 2006).
    • "Exploiting DOM for Web response" (Web yanıtı için DOM'yi kullanma) başlıklı Bölüm 4'te DOM tanıtılır ve HTML'nin bir nesne modeline dönüştürülmesinin Web sayfalarını nasıl yanıt verebilir ve etkileşimli kıldığı anlatılır (Mart 2006).

  • Use Ajax with WebSphere Portal (Ajax'ı WebSphere Portal ile kullanma), portal performansını artırmak, daha temiz bir portal uygulaması mimarisi ve -- en önemlisi -- kullanıcılarınıza çok daha hızlı yanıt veren bir portal yaratmak için. (developerWorks, Haziran 2006)

  • Ajax for Java developers: Build dynamic Java applications, Philip McCarthy: Java bakış açısını kullanarak sunucu tarafından Ajax'a bakın ve dinamik Web uygulaması deneyimleri oluşturmak için çığır açan bir yaklaşımla tanışın (developerWorks, Eylül 2005).

  • Ajax for Java developers: Java object serialization for Ajax, Philip McCarthy: Java nesnesi diziselleştirmesine ilişkin beş yaklaşımı inceleyin ve ağ üzerinden nesneleri nasıl göndereceğinizi ve Ajax ile nasıl etkileşime geçeceğinizi öğrenin (developerWorks, Ekim 2005).

  • Call SOAP Web services with Ajax, Part 1: Build the Web services client, James Snell: Ajax'ın var olan SOAP tabanlı Web hizmetleriyle bütünleştirilmesine ilişkin bu ileri düzey makaleyi inceleyin; Ajax tasarım şablonunu kullanarak Web tarayıcısı tabanlı SOAP Web hizmetleri istemcisini nasıl uygulayacağınızı gösterir (developerWorks, Ekim 2005).

  • Ajax: A New Approach to Web Applications: Ajax moniker teriminin ilk kez kullanıldığı bu makaleyi okuyun -- tüm Ajax geliştiricileri bu makaleyi okumalıdır.

  • World Wide Web Consortium'daki DOM Ana Sayfası: DOM ile ilgili her şeyin başlangıç noktası olan bu siteyi ziyaret edin.

  • DOM Level 3 Core Specification (DOM Düzey 3 Çekirdek Belirtimi): Çeşitli dillerden Belge Nesne Modeli'nin kullanabileceği tipleri ve özellikleri kullanarak çekirdek DOM'yi tanımlayın.

  • ECMAScript language bindings for DOM (DOM için ECMAScript dil ilişkilendirmeleri): Bir JavaScript programcısıysanız ve kodunuz için DOM kullanmak istiyorsanız, Düzey 3 Belge Nesne Modeli Çekirdeği tanımlarına ilişkin bu ek ilginizi çekecektir.

  • developerWorks Web mimarisi alanı: Web oluşturma becerilerinizi makaleler, senaryolar, forumlar, vb. araçlarla genişletin.

  • developerWorks teknik etkinlikleri ve Web yayınları: Teknik geliştiricilere yönelik bu yazılım brifinglerini takip edin.


Ürün ve teknoloji edinme
  • Head Rush Ajax, Brett McLaughlin (O'Reilly Media, Inc., Mart 2006): Bu makaledeki fikirleri Head First yöntemiyle öğrenin.

  • Java and XML, İkinci Basım, Brett McLaughlin (Ağustos 2001, O'Reilly Media, Inc.): Yazarın, XHTML ve XML dönüşümleriyle ilgili düşüncelerini okuyun.

  • JavaScript: The Definitive Guide, David Flanagan (Kasım 2001, O'Reilly Media, Inc.): JavaScript ve dinamik Web sayfalarıyla çalışmaya ilişkin kapsamlı yönergeleri inceleyin. Yayınlanacak olan yeni basımda Ajax ile ilgili iki yeni bölüm vardır.

  • Head First HTML with CSS & XHTML, Elizabeth ve Eric Freeman (Aralık 2005, O'Reilly Media, Inc.): Standartlaşmış HTML ve XHTML ve CSS'yi HTML'ye uygulamayla ilgili daha fazla bilgi öğrenin.

  • IBM deneme yazılımı: developerWorks'deki yazılımı doğrudan yükleyerek bir sonraki geliştirme projenizi oluşturun.

Tartışma

Yazar hakkında

Brett McLaughlin'in fotoğrafı

Brett McLaughlin, Logo günlerinden bu yana bilgisayarlarla ilgili çalışmalar yapmaktadır (Küçük üçgeni hatırlıyor musunuz?) Son yıllarda, Java ve XML topluluklarında en çok tanınan yazarlardan ve programcılardan biri oldu. Kendisi, Nextel Communications şirketi için karmaşık kurumsal sistemler uygulaması, Lutric Technologies için uygulama sunucuları yazma görevlerini üstlendi ve en son O'Reilly Media, Inc. için önemli kitaplar yazma ve yayına hazırlama işlerini yürütüyor. Brett'in, yeni kitabı Head Rush Ajax, Ajax'a Head First adlı ödüllü ve yenilikçi bir yaklaşım getiriyor. Son kitabı Java 1.5 Tiger: A Developer's Notebook, Java teknolojisinin en yeni sürümüyle ilgili ilk kitap olma özelliğini taşıyor. Artık bir klasik olan Java and XML adlı kitabı ise, Java dilinde XML teknolojilerinin kullanılması üzerine en açıklayıcı çalışma olmaya devam ediyor.

Görüşler

0
ramesaliyev
Yalnız şöyle bir durum var burada, Liste 1. DOM içinde düğüm özelliklerinin kullanılması" örneğini html içerisine alıp kullanmak isteyecek arkadaşlar (ki ben yaptım bunu) bir sorunla karşılaşacaklardır. bodyElement null değeriyle döneceğinden nodeName de undefined olacaktır.

Yani;

var bodyElement = headElement.nextSibling; while (bodyElement.nodeName.toLowerCase() != "body") { bodyElement = bodyElement.nextSibling; }
kod bloğunun altına şunu eklerseniz;
alert(bodyElement.nodeName);
alert filan alamazsınız. (örnek ben orada iyice anlayabilmek için body'nin de nodenamesini çekeyim demiştim) Bunun nedeni benim anladığım kadarıyla bu kodlar (javascript kodları) işlendiği zaman daha "body" elementinin oluşturulmamış olmasıdır. Lakin daha sonraki

Liste 3. DOM'nin kullanıldığı bazı JavaScript kodlarının bulunduğu bir HTML dosyası örneğinde bu kodlar bir fonksiyon ile çalıştırıldığında body kullanılabiliniyor.

Zaten daha önceki yazıda da DOM ile ancak oluşturulmuş elementleri düzenleyebilirsiniz denilmişti, daha yüklenmemişleri değil tabiki.

Yani eğer sayfanız yüklenir yüklenmez body ile ilgili bir şeyler yapmak istiyorsanız, bu DOM işlemini bir window.onload fonksiyonuna atamayı unutmayın.

Sanırım çok konuştum. Saygı sevgiler.
0
ramesaliyev

Öznitelik düğümleri kısmındaki for döngüsünde hata var.

for (i=0; i<imgElements.length; i++) {
olarak yazılmış lakin burdaki img'ler silindiğinden döngü her döndüğünde imgElements.length değeri 1 eksilmektedir. E bu durumda da i = 10 ve kalan resimler = 10 olduğunda işlem kapanıyor. sonra 5 olunca sonra 2 sonra 1. Yarı yarıya bölüyor yani kendini doğal olarak. Bunu aşmak için kodu şöyle düzenledim.
imgElementsLength = imgElements.length; for (i=0; i<imgElementsLength; i++) {
0
ramesaliyev


Bir önceki yorumum yanlış olmuş, hata farklı bir yerdeymiş;

Öznitelik düğümleri kısmında kod hatası bulunmakta, birkaç şey atlanmış.

for (i=0; i-1; i--) {

Veya sürekli 0. itemi silmek için;

var imgElement = imgElements.item(0)
0
ramesaliyev
Bir önceki yorumum yanlış olmuş, hata farklı bir yerdeymiş;Öznitelik düğümleri kısmında kod hatası bulunmakta, birkaç şey atlanmış.

for (i=0; i<imgElements.length; i++) {
var imgElement = imgElements.item[i];

olarak yazılan kodda syntax hatası : imgElements.item[i] yerine imgElements.item(i) olmalı yani köşeli değil normal parantezlerle.

Bundan ayrı olarak daha ciddi bir hata var ki o da şudur; For döngüsü i'yi 0dan büyütmeye başlıyor lakin elementlerin sayısı gittikçe düşüyor.
Örnekle açıklamak daha sağlıklı olacak; 20 resmimiz varsa, i gittikçe büyürken 10a geldi diyelim, diğer taraftan da resimlerimiz 1'den başlayarak 10a kadar silindi. Mesele şu ki her element silindiğinde item listesinin sırası geriye doğru kayıyor: Yani mesela 2numaralı item 1 numaraya geliyor. E zaten mantıklısı da bu. İşte burada bir çakışma meydana geliyor. Diyelim ki döngü 10 kez döndü ve i = 10 oldu, element sayısı da 10 kere silindiği için sürekli geriye doğru kaydı ve 20-10 = kaldı 10 element, lakin i kaldığı yerden devam ediyor ve 11. itemi silmeye çalışıyor. Durum böyle olunca 11. item olmadığından hata oluşuyor ve döngü yarıda kesiliyor. Toplam item sayısının yarısında oluşuyor sürekli bu olay, i'nin imgElements.length'i aştığı yerde yani.

Peki bunu nasıl aşabiliriz ?

Bunu aşmak için iki yöntem var ya döngüyü tersten başlatacağız. Ya da item silerken sürekli 0. itemi sileceğiz. Tersten başlatmak için;
for (i=imgElements.length-1; i>-1; i--) {

Veya sürekli 0. itemi silmek için;
var imgElement = imgElements.item(0)
0
ramesaliyev
Tabi sürekli sadece 0. itemi sileceksek, for döngüsünüde düzeltmeliyiz

for (i=0; i<imgElements.length; i++) {
olarak yazılmış lakin burdaki img'ler silindiğinden döngü her döndüğünde imgElements.length değeri 1 eksilmektedir. E bu durumda da i = 10 ve kalan resimler = 10 olduğunda işlem kapanıyor. sonra 5 olunca sonra 2 sonra 1. Yarı yarıya bölüyor yani kendini doğal olarak. Bunu aşmak için kodu şöyle düzenledim.
imgElementsLength = imgElements.length;
for (i=0; i<imgElementsLength; i++) {
Görüş belirtmek için giriş yapın...

İlgili Yazılar

Ajax Konusunda Uzmanlaşma, Bölüm 7

butch

IBM Türkiye ve Fazlamesai.net işbirliği ile dilimize kazandırılan yeni bir IBM developerWorks makalesi ile karşınızdayız. Diğer makalelere buradan ulaşabilirsiniz.

Makalenin özgün haline bu adresten ulaşabilirsiniz.

Yeni kullanıcılar için UNIX ipuçları Bölüm 3: Süzgeçler ve düzenli ifadeler

tongucyumruk

IBM Türkiye ve Fazlamesai.net işbirliği ile dilimize kazandırılan yeni bir IBM developerWorks makalesi ile karşınızdayız. Diğer makalelere buradan ulaşabilirsiniz.

Makalenin özgün haline bu adresten ulaşabilirsiniz.

UNIX Dilinde Konuşma, Bölüm 6: Her şeyi otomatikleştirin!

butch

IBM Türkiye ve Fazlamesai.net işbirliği ile dilimize kazandırılan yeni bir IBM developerWorks makalesi ile karşınızdayız. Diğer makalelere buradan ulaşabilirsiniz.

Makalenin özgün haline bu adresten ulaşabilirsiniz.

Linux çalıştıran bilgisayarınızın performansını müzikal olarak gözetleyin

butch

Emre Sevinç tarafından dilimize kazandırılan yeni bir IBM developerWorks makalesi ile karşınızdayız.

Makalenin özgün haline bu adresten ulaşabilirsiniz.

UNIX Dilinde Konuşma, Bölüm 2: Daha çok değil, daha akıllı çalışma

tongucyumruk

IBM Türkiye ve Fazlamesai.net işbirliği ile dilimize kazandırılan yeni bir IBM developerWorks makalesi ile karşınızdayız. Diğer makalelere buradan ulaşabilirsiniz.

Makalenin özgün haline bu adresten ulaşabilirsiniz.