Jonas: Probleme mit dem erstellen neuer Knoten (DOM) in IE

Hallo zusammen

Ich arbeite gerade an einem Script, welches neue "Div-Konstrukte" erstellt.

In FireFox funktioniert auch alles wunderbar, der Internet Explorer hingegen meldet "Unerwarteter Aufruf oder Zugriff".

Google konnte mir bis jetzt nicht weiterhelfen, und nach dieser Erklährung http://de.selfhtml.org/dhtml/modelle/dom.htm#neue_knoten sollte es funktionieren.

Das Script befindet sich im Moment hier:
http://buro.sequenz.net/dev/res/script/divWindow.js

Und hier das Beispiel:
http://buro.sequenz.net/dev/divtest.html

Das die Transparenz des png Hintergrundes im IE nicht funktioniert ist mir klar...

Vielen Dank schon im Voraus.

Grüsse
Jonas

  1. Hi,

    http://buro.sequenz.net/dev/res/script/divWindow.js

    Du weisst um IEs Probleme mit setAttribute, wenn die Eigenschaft auch direkt ansprechbar ist?
    Beispiel: handleDiv.setAttribute("class","leiste") versus handleDiv.className = "leiste".
    Du weisst ferner dass javascript im href böse ist und wenn, dann mit void?

    Gruesse, Joachim

    --
    Am Ende wird alles gut.
    1. Hallo

      Du weisst um IEs Probleme mit setAttribute, wenn die Eigenschaft auch direkt ansprechbar ist?
      Beispiel: handleDiv.setAttribute("class","leiste") versus handleDiv.className = "leiste".

      Nein, wusste ich nicht, danke für den Hinweis, werde mich dann mal dementsprechend dahinter machen.

      Du weisst ferner dass javascript im href böse ist und wenn, dann mit void?

      Wusste ich auch nicht! Weisses jetzt aber, ich nehms mir zu Herzen, bin immer froh wenn mich jemand über Do's und Dont's aufklärt!

      Ich danke dir für die schnelle Antwort! Ich werde die Lösung Posten sobald es funktioniert.

      Gruss
      Jonas

      1. Du weisst um IEs Probleme mit setAttribute, wenn die Eigenschaft auch direkt ansprechbar ist?
        Beispiel: handleDiv.setAttribute("class","leiste") versus handleDiv.className = "leiste".
        Nein, wusste ich nicht, danke für den Hinweis, werde mich dann mal dementsprechend dahinter machen.

        Das betrifft übrigens alle deine setAttribute Zuweisungen. Du dürftest dann mit den Event Handlern Probleme bekommen.

        aber erstmal:
        buttonMinimize.setAttribute("href","#");

        Solange du keinen Link setzen willst lass das href Attribut einfach so  wie es ist, du musst nur die onclick Funktion mit einem return false beenden. wobei, wenn du eh keinen Link brauchst soltest du auch kein Linkelement verwenden, nimm einfach ein <span> Element, das kennt wie alle anderen auch den onclick Event.

        Die Events sehen dann in etwa so aus:

        handleDiv.onmouseover = function(e)
        {
        gotop(idRoot);
        }

        allerdings ist dass nicht schön, da du einerseits das Element mit der id ja schon hast folglich nicht jedesmal mit getElement neu holen musst und anderseits idRoot unter Umständen, wenn du die Funktion ehrmals aufrufst, etwas anderes ist als du erwartest (es hat immer den Wert des letzten Aufrufs).

        Besser wäre es in etwa so:

        var rootDiv = document.createElement('div');  
        rootDiv.style = "left:60px; top:130px; z-index:100;"; // position:absolute wäre noch gut  
        ...  
        handleDiv.rootEl = rootDiv;  
        handleDiv.onmouseover = function(e)  
        {  
        gotop(this.rootEl);  
        }  
          
        function gotop(o)  
        {  
         iIndex++  
         o.style.zIndex = iIndex;  
        }
        

        Ausserdem solltest du die Variabeln lokal machen. Globale Variabeln können u.U. zu Fehlern führen die sehr schwer zu finden sind.

        Struppi.

        1. Hi,

          Das betrifft übrigens alle deine setAttribute Zuweisungen. Du dürftest dann mit den Event Handlern Probleme bekommen.

          Ja, in der Tat hatte ich Probleme mit den Event Handlern, gut das ich jetzt weiss woran das liegt!

          aber erstmal:
          buttonMinimize.setAttribute("href","#");

          Solange du keinen Link setzen willst lass das href Attribut einfach so  wie es ist, du musst nur die onclick Funktion mit einem return false beenden. wobei, wenn du eh keinen Link brauchst soltest du auch kein Linkelement verwenden, nimm einfach ein <span> Element, das kennt wie alle anderen auch den onclick Event.

          Werde ich machen! War eh ein bisschen unglücklich mit diesen Links die gar keine Links sind...

          var rootDiv = document.createElement('div');

          rootDiv.style = "left:60px; top:130px; z-index:100;"; // position:absolute wäre noch gut

          ...

          »»

            
          Wow! Vielen Dank für die ausführliche Antwort, von solchen Antworten hab ich nicht zu träumen gewagt ;-)!  
          Ich werde das Script noch ein mal von Grund auf überarbeiten.  
            
          Was ich nicht ganz verstehe:  
          ~~~javascript
          var rootDiv = document.createElement('div');  
          rootDiv.style = "left:60px; top:130px; z-index:100;"; // position:absolute wäre noch gut  
          //--> positioniere ich im externen Stylesheet, diese Angaben sind nur da, damit das 'DragScript' funktioiert  
          ...  
          handleDiv.rootEl = rootDiv;  
          handleDiv.onmouseover = function(e) //Für was ist das (e) gut?  
          {  
          gotop(this.rootEl);  
          }  
            
          function gotop(o) //und für was das (o)?  
          {  
           iIndex++  
           o.style.zIndex = iIndex;  
          }  
          
          

          Was für Werte werden da übergeben?

          Vielen Dank und Grüsse
          Jonas

          1. Was ich nicht ganz verstehe:

            ...

            handleDiv.rootEl = rootDiv;
            handleDiv.onmouseover = function(e) //Für was ist das (e) gut?

            Nur zur Sicherheit, Mozilla Browser übergeben den Event als Parameter, falls du in der Funktion wissen willst wer, wo und wie den Event ausgelöst hat.

            {
            gotop(this.rootEl);
            }

            function gotop(o) //und für was das (o)?

            Der Parameter this.rootEl.

            Folgendermaßen:

            1. erzeugst du ein Element, du nennst es rootDiv
            rootDiv = document.createElement(....);

            2. Dann erzeugst du das handleDiv
            handleDiv = document.createElement(....);

            3. Damit du nachher im Eventhandler an dass rootDiv kommst, setzt du eine neue Eigenschaft im handleDiv
            handleDiv.rootEl = rootDiv;

            4. weil du in der Eventfunktion mit *this* das Objekt handleDiv ansprichst, kannst du dann mit this.rootEl auf das rootDiv zugreifen
            handleDiv.onmouseover = function(e)
            {
            gotop(this.rootEl);
            }

            (Zur Erläuterung: Wenn du irgendwo einen Event so deklarierst:
            objekt.onevent = function() { .... Dann ist hier in der Funktion this immer das objekt)

            5. In der gotop Funktion brauchst du dann nicht mehr getElementById, sondern hast direkt das Objekt (daher o) dass du manipulieren willst.
            o.style.zIndex = iIndex;

            Struppi.

            1. Danke für die Erklärung werde mich heute Abend daran machen und das Script neu schreiben.
              Ich werde meine neuen Erkenntnisse Posten!

              Nocheimal Dank für die guten Antworten, hab in kurzer Zeit einiges gelernt.

              Grüsse Jonas

              1. Ich habe leider den neuen (jetzt funktionierenden) Code immer noch nicht online gestellt!

                Aber was ich sagen kann, das Hauptproblem war, dass der Internet Explorer für 'Script-Elemente' keine Kindknoten akzeptiert.

                Umgehen kann man das Problem folgendermassen:

                  
                var scriptnode = document.createElement('script');  
                scriptnode.text = "Hier der Text";  
                
                

                Funktioniert in Firefox und IE. Tja, das wars!

                Noch mal Danke für die Hilfe!

                1. Aber was ich sagen kann, das Hauptproblem war, dass der Internet Explorer für 'Script-Elemente' keine Kindknoten akzeptiert.

                  was für Kindknoten willst du den Script Elementen zuweisen?

                  var scriptnode = document.createElement('script');
                  scriptnode.text = "Hier der Text";

                  
                  >   
                  > Funktioniert in Firefox und IE. Tja, das wars!  
                    
                  Was für einen Sinn hat das?  
                    
                  Struppi.
                  
                  -- 
                  [Javascript ist toll](http://javascript.jstruebig.de/)
                  
                  1. was für Kindknoten willst du den Script Elementen zuweisen?

                    Was für einen Sinn hat das?

                    Ich kann ein Script dynamisch erstellen, ich weiss,weiss man mit anderen Möglichkeit dasselbe erreichen kann, aber es erschien mir einfach und praktisch.
                    Und ausserdem es doch Spass ein Script dynamisch zu erstellen ;-] ...

                    Bei meinem Beispiel brauche ich es um die generierten 'div's dragable zu machen, ich möchte das Script jeweils in dem Betroffenen 'div-Element' drin haben... Wie gesagt, mir ist klar, dass man das auch anders lösen kann.

                    Gruss
                    Jonas

                    1. was für Kindknoten willst du den Script Elementen zuweisen?

                      Was für einen Sinn hat das?
                      Ich kann ein Script dynamisch erstellen, ich weiss,weiss man mit anderen Möglichkeit dasselbe erreichen kann, aber es erschien mir einfach und praktisch.

                      Wieso soll man mit einem Skript ein Skript dynamisch erstellen????
                      du hast doch dass Skript dann schon?
                      Das klingt IMHO eher umständlich und unpraktisch. Du kannst doch jede Funktion, mit einem Objekt verbinden, dazu reicht i.d.R. eine einfach Zuweisung.

                      Wenn du ein Skript nachträglich laden willst, kannst du es auch so probieren:
                          var s = document.createElement('script');
                          s.src = 'test.js';
                          document.body.appendChild(s);

                      Aber ein Skriptelement hat halt keine (HTML) Kindknoten.

                      Struppi.

                      1. Wenn du ein Skript nachträglich laden willst, kannst du es auch so probieren:
                            var s = document.createElement('script');
                            s.src = 'test.js';
                            document.body.appendChild(s);

                        Aber ein Skriptelement hat halt keine (HTML) Kindknoten.

                        Hm, ja, du hast natürlich recht. Das wär umeiniges eleganter und auch einfacher. Wie bringe ich dann da jetzt verschiedenen Parameter rein.

                        Ich glaub ich steh bei der Sache ein bisschen auf dem Schlauch!

                        Gruss
                        GrussJonas

                        1. Aber ein Skriptelement hat halt keine (HTML) Kindknoten.

                          Hm, ja, du hast natürlich recht. Das wär umeiniges eleganter und auch einfacher. Wie bringe ich dann da jetzt verschiedenen Parameter rein.

                          Ist das eine Frage! ;-)

                          Wie meinst du das? Was für Parameter?

                          Struppi.

                          1. Ist das eine Frage! ;-)

                            Wie meinst du das? Was für Parameter?

                            Na die Sache ist die, ich brauche pro generiertem 'div-Konstrukt' ein Aufruf der 'div-drag-Funktion' mit jeweils den 'id's der zu 'dragenden'  'div's...
                            Also, so in etwa das:

                              
                            <script type="text/javascript">  
                                var theHandle = document.getElementById("han1");  
                                var theRoot = document.getElementById("win1");  
                                Drag.init(theHandle, theRoot);  
                            </script>  
                            
                            

                            Gruss
                            Jonas

                            1. Wie meinst du das? Was für Parameter?

                              Na die Sache ist die, ich brauche pro generiertem 'div-Konstrukt' ein Aufruf der 'div-drag-Funktion' mit jeweils den 'id's der zu 'dragenden'  'div's...

                              Du kannst mehrere Elemente auf einmal "Draggen"?
                              Und wieso willst du deshalb Skripte dynamisch nachladen?
                              Ist es nicht sinnvoller, ein Skript normal einzubinden und dann "onmousedown" ermitteln ob und welches Element gezogen werden soll?

                              Deine Vorgehensweise scheint mir nicht sinnvoll, da du das Problem hast (das immer beim dynamischen Nachladen auftritt), dass du nur schwer kontrollieren kannst wann das Skript fertig geladen ist, also bereit ist zum benutzen, letztlich kannst du das nur in dem zu ladenen Skript kontrollieren.

                              Struppi.

                              1. Ist es nicht sinnvoller, ein Skript normal einzubinden und dann "onmousedown" ermitteln ob und welches Element gezogen werden soll?

                                Das ist auf jedenfall eleganter. Allerdings muss ich dann so einiges umschreiben.

                                Deine Vorgehensweise scheint mir nicht sinnvoll, da du das Problem hast (das immer beim dynamischen Nachladen auftritt), dass du nur schwer kontrollieren kannst wann das Skript fertig geladen ist, also bereit ist zum benutzen, letztlich kannst du das nur in dem zu ladenen Skript kontrollieren.

                                Ich bin auch nicht wirklich glücklich mit meiner Lösung, aber wie gesagt, ich müsste wohl einiges neu schreiben und dafür fehlt mir im Moment leider die Zeit.

                                Gruss
                                Jonas