Partage
  • Partager sur Facebook
  • Partager sur Twitter

Une fonction JS qui ne marche que sous IE

Je voudrais la rendre un peu plus propre

    4 mars 2010 à 13:52:41

    Bonjour à tous,

    Dans le cadre du projet sur lequel je travaille actuellement, le client a émis il y a quelques temps (avant que j'arrive) le besoin d'avoir un champ <select> éditable.

    Pour réaliser ceci, je me retrouve avec une fonction javascript qui marche sous IE6 mais pas sous FF 3.6
    Je met ci-dessous le code de cette fonction.
    Mon but n'est pas que vous recodiez la fonction à ma place, mais plutôt que vous m'expliquiez quelles sont les "bonnes pratiques" en javascript à appliquer à cette fonction pour la rendre plus "stable".

    Pas la peine de me dire :
    "ton code c'est de la merde" ou des trucs dans le genre
    Parce que, ce code n'est pas le mien et qu'avec mes maigres connaissances en JS je me suis rendu compte tout seul que ce code n'était pas très "propre".


    Je vous remercie par avance :)

    function createEditableSelect(dest)
    	{
    
    		dest.className='selectBoxInput';		
    		var div = document.createElement('DIV');
    		div.style.styleFloat = 'left';
    		div.style.width = dest.offsetWidth + 16 + 'px';
    		div.style.position = 'relative';
    		div.id = 'selectBox' + selectBoxIds;
    		var parent = dest.parentNode;
    		parent.insertBefore(div,dest);
    		div.appendChild(dest);	
    		div.className='selectBox';
    		div.style.zIndex = 10000 - selectBoxIds;
    
    		var img = document.createElement('IMG');
    		img.src = arrowImage;
    		img.className = 'selectBoxArrow';
    		
    		img.onmouseover = selectBox_switchImageUrl;
    		img.onmouseout = selectBox_switchImageUrl;
    		img.onclick = selectBox_showOptions;
    		img.id = 'arrowSelectBox' + selectBoxIds;
    
    		div.appendChild(img);
    		
    		var optionDiv = document.createElement('DIV');
    		optionDiv.id = 'selectBoxOptions' + selectBoxIds;
    		optionDiv.className='selectBoxOptionContainer';
    		optionDiv.style.width = div.offsetWidth-2 + 'px';
    		div.appendChild(optionDiv);
    		
    		if(navigator.userAgent.indexOf('MSIE')>=0){
    			var iframe = document.createElement('<IFRAME src="about:blank" frameborder=0>');
    			iframe.style.width = optionDiv.style.width;
    			iframe.style.height = optionDiv.offsetHeight + 'px';
    			iframe.style.display='none';
    			iframe.id = 'selectBoxIframe' + selectBoxIds;
    			div.appendChild(iframe);
    		}
    		
    		if(dest.getAttribute('selectBoxOptions')){
    			var options = dest.getAttribute('selectBoxOptions').split(';');
    			var optionsTotalHeight = 0;
    			var optionArray = new Array();
    			for(var no=0;no<options.length;no++){
    				var anOption = document.createElement('DIV');
    				anOption.innerHTML = options[no];
    				anOption.className='selectBoxAnOption';
    				anOption.onclick = selectOptionValue;
    				anOption.style.width = optionDiv.style.width.replace('px','') - 2 + 'px'; 
    				anOption.onmouseover = highlightSelectBoxOption;
    				optionDiv.appendChild(anOption);	
    				optionsTotalHeight = optionsTotalHeight + anOption.offsetHeight;
    				optionArray.push(anOption);
    			}
    			if(optionsTotalHeight > optionDiv.offsetHeight){				
    				for(var no=0;no<optionArray.length;no++){
    					optionArray[no].style.width = optionDiv.style.width.replace('px','') - 22 + 'px'; 	
    				}	
    			}		
    			optionDiv.style.display='none';
    			optionDiv.style.visibility='visible';
    		}
    		
    		selectBoxIds = selectBoxIds + 1;
    	}
    



    Dans ma JSP, la fonction est appelée comme ceci :
    <script type="text/javascript">
    var j=0;
    var tmp=new Array();
    var listeCodeRisque ="";
    <logic:iterate id="code" name="contenant" property="listcoderisque">	
    	tmp[j++] = "<bean:write name="code" property="value"/>";	
    </logic:iterate>
    for(var i=0;i<tmp.length;i++){
    	if (i==0){
    		listeCodeRisque = tmp[i];
    	}else{
    		listeCodeRisque = listeCodeRisque +";"+ tmp[i];
    	}
    }
    var codeRisque = "<bean:write name="contenant" property="codeRisque"/>";	
    if (null!=document.forms[0].selectEditRisque){
    	document.forms[0].selectEditRisque.selectBoxOptions = listeCodeRisque;
    	document.forms[0].selectEditRisque.value = codeRisque;
    	createEditableSelect(document.forms[0].selectEditRisque);
    }
    </script>
    

    • Partager sur Facebook
    • Partager sur Twitter

    Si y'a pas d'accents dans mes messages c'est parce que je suis sur un clavier norvegien :)

      4 mars 2010 à 14:11:30

      Salut,

      Le code n'est pas si sale que ça.
      Par contre j'avoue que ça:
      <logic:iterate id="code" name="contenant" property="listcoderisque">	
      	tmp[j++] = "<bean:write name="code" property="value"/>";	
      </logic:iterate>
      

      ça me reste en travers de la gorge, c'est quoi cette horreur ? ça marche en javascript ? Perso j'ai jamais vu.
      Regarde dans le debug JS de firefox si ça cloche pas là dessus.

      Sinon les trucs dégueulasses les voilà:
      var iframe = document.createElement('<IFRAME src="about:blank" frameborder=0>');
      

      ça ne concerne qu'ie donc on s'en fiche un peu mais bon, c'est atroce.

      anOption.onmouseover = highlightSelectBoxOption;
      

      Evènements à la volée, ça fonctionne mais c'est déconseillé !

      div.style.width = dest.offsetWidth + 16 + 'px';
      

      En théorie ça devrait passer mais concaténer et en même temps additionner... Je ne sais pas ce que donne la pratique !

      var img = document.createElement('IMG');
      

      Les noms en majuscule, bon, moi je le fais pas je trouve pas ça beau mais là on passe à l'esthétique :D .

      J'espère que je t'aurais aidé.
      • Partager sur Facebook
      • Partager sur Twitter
      Venez sur Zeste de Savoir, on est bien :-) . Mon tuto PHPSpec.
        4 mars 2010 à 14:16:55

        Merci pour tes conseils/indications :)

        La partie "<logic:iterate" etc...C'est du code struts...c'est une sorte de surcouche au HTML/JSP. Par contre, c'est très moche ^^
        Je me rends compte que je ne suis pas en mesure (parce que je ne m'y connais pas assez en JS) de corriger/améliorer cette fonction et ça m'énerve un peu...

        En gros, pour faire fonctionner cette fonction sous FF, y'a-t-il "beaucoup" de boulot ?
        La fonction doit-elle être repensée entièrement ?
        • Partager sur Facebook
        • Partager sur Twitter

        Si y'a pas d'accents dans mes messages c'est parce que je suis sur un clavier norvegien :)

          4 mars 2010 à 14:17:49

          Citation : Nek'


          anOption.onmouseover = highlightSelectBoxOption;
          


          Evènements à la volée, ça fonctionne mais c'est déconseillé !



          Tu peux expliciter ça ? Je vois pas où est le problème dans son code... :euh:
          • Partager sur Facebook
          • Partager sur Twitter
            4 mars 2010 à 15:22:52

            Citation : Golmote

            Citation : Nek'


            anOption.onmouseover = highlightSelectBoxOption;
            


            Evènements à la volée, ça fonctionne mais c'est déconseillé !



            Tu peux expliciter ça ? Je vois pas où est le problème dans son code... :euh:



            J'ai pas dit qu'il y avait un problème, mais on m'a toujours dit que c'était mieux d'utiliser addEventListener().

            Sinon nan il ne doit pas y avoir grand chose à changer, je me répète mais as-tu été voir du côté des erreurs javascript de firefox ?
            Ça pourra surement nous aider.
            • Partager sur Facebook
            • Partager sur Twitter
            Venez sur Zeste de Savoir, on est bien :-) . Mon tuto PHPSpec.
              4 mars 2010 à 15:24:11

              >>div.style.width = dest.offsetWidth + 16 + 'px';
              div.style.width = (parseInt(dest.offsetWidth) + 16) + 'px';
              • Partager sur Facebook
              • Partager sur Twitter
                4 mars 2010 à 15:34:56

                Citation : birdy42

                >>div.style.width = dest.offsetWidth + 16 + 'px';
                div.style.width = (parseInt(dest.offsetWidth) + 16) + 'px';


                Dans ce cas à faire aussi ici:
                anOption.style.width = optionDiv.style.width.replace('px','') - 2 + 'px';
                

                anOption.style.width = (optionDiv.offsetWidth - 2) + 'px';
                


                Edit: bonne remarque birdy42, mais bon là tant qu'à faire autant carrément prendre la taille directement x').
                • Partager sur Facebook
                • Partager sur Twitter
                Venez sur Zeste de Savoir, on est bien :-) . Mon tuto PHPSpec.
                  4 mars 2010 à 15:46:42

                  parseInt vire le "px" tout seul. pas besoin du replace ;) (et en plus c'est plus rapide :-°)
                  • Partager sur Facebook
                  • Partager sur Twitter
                    4 mars 2010 à 20:39:58

                    Ouais mais le parseInt, tu lui mets 10 en deuxième paramètre ! Au cas où ;)
                    • Partager sur Facebook
                    • Partager sur Twitter

                    Une fonction JS qui ne marche que sous IE

                    × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
                    × Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
                    • Editeur
                    • Markdown