2009-12-22 5 views
161

J'essaie d'utiliser un bouton HTML pour appeler une fonction JavaScript.Utilisation d'un bouton HTML pour appeler une fonction JavaScript

Voici le code:

<input type="button" value="Capacity Chart" onclick="CapacityChart();"> 

Il ne semble pas fonctionner correctement si. Y a-t-il une meilleure manière de faire cela?

Voici le lien: http://projectpath.ideapeoplesite.com/bendel/toolscalculators.html cliquez sur l'onglet capacité dans la section inférieure gauche. Le bouton devrait générer une alerte si les valeurs ne sont pas modifiées et devrait produire un graphique si vous entrez des valeurs.

+4

s'il vous plaît définir « doesn ne semble pas fonctionner correctement ". quelle (s) erreur (s) obtenez-vous lorsque vous cliquez dessus? –

+0

Le bouton fonctionne dans IE8, mais pas FF 3.5 en raison d'une erreur JavaScript (voir la réponse de Jeff) –

+0

Oui, il s'avère que document.all est une chose non standard d'IE; mis à jour ma réponse avec une alternative proposée. – Jeff

Répondre

258

Il existe plusieurs façons de gérer les événements avec HTML/DOM. Il n'y a pas vraiment de bonne ou de mauvaise façon mais différentes façons sont utiles dans différentes situations.

1: Il y a la définition dans le code HTML:

<input id="clickMe" type="button" value="clickme" onclick="doFunction();" /> 

2: Il y a l'ajouter à la propriété DOM pour l'événement en Javascript:

//- Using a function pointer: 
document.getElementById("clickMe").onclick = doFunction; 

//- Using an anonymous function: 
document.getElementById("clickMe").onclick = function() { alert('hello!'); }; 

3: Et il y a la fixation d'une fonction le gestionnaire d'événements utilisant Javascript:

var el = document.getElementById("clickMe"); 
if (el.addEventListener) 
    el.addEventListener("click", doFunction, false); 
else if (el.attachEvent) 
    el.attachEvent('onclick', doFunction); 

Les deux méthodes permettent l'inline/anonymou Les fonctions s et les deux doivent être déclarées après que l'élément a été analysé à partir du document. La première méthode n'est pas XHTML valide car l'attribut onclick n'est pas dans la spécification XHTML.

Les 1ère et 2ème méthodes sont mutuellement exclusives, ce qui signifie que l'utilisation de l'une (la 2ème) remplacera l'autre (la 1ère). La troisième méthode vous permettra d'attacher autant de fonctions que vous le souhaitez au même gestionnaire d'événements, même si la première ou la deuxième méthode a été utilisée aussi. Le problème est probablement lié à votre fonction CapacityChart(). Après avoir visité votre lien et exécuté votre script, la fonction CapacityChart() s'exécute et les deux popups sont ouverts (un est fermé selon le script).Où vous avez la ligne suivante:

CapacityWindow.document.write(s); 

Essayez les options suivantes à la place:

CapacityWindow.document.open("text/html"); 
CapacityWindow.document.write(s); 
CapacityWindow.document.close(); 

EDIT
Quand j'ai vu votre code Je pensais que vous écrivez spécifiquement pour IE. Comme d'autres l'ont mentionné, vous devrez remplacer les références à document.all par document.getElementById. Cependant, vous aurez toujours la tâche de réparer le script après cela, donc je vous recommande de le faire fonctionner au moins dans IE au début, car toute erreur que vous faites en changeant le code pour travailler dans le navigateur pourrait causer encore plus de confusion. Une fois qu'il fonctionne dans IE, il sera plus facile de savoir si cela fonctionne dans d'autres navigateurs pendant que vous mettez à jour le code.

+3

En utilisant jquery, il y a aussi: '$ (" # clickMe ") .bind ('click', function() {alert ('bonjour!');};)' – Roman

-1

façon stupide:

onclick="javascript:CapacityChart();" 

Vous devriez lire le Javascript discret et utiliser une méthode de liaison de cadres pour lier callbacks dom événements.

+0

J'ai essayé cela et j'ai toujours les mêmes résultats - rien. – fmz

+0

@erenon: Oh, allez. Ce n'est pas son problème, la notation est parfaitement correcte, et il n'y a aucune raison d'entrer dans des bindings et des frameworks compliqués juste pour assigner un événement onclick. –

+0

Merci d'être venu à ma défense Pekka. Je veux juste un bouton simple pour fonctionner correctement. – fmz

22

Je dirais qu'il serait préférable d'ajouter le javascript d'une manière non importune ...

si vous utilisez jQuery, vous pouvez faire quelque chose comme:

<script> 
    $(document).ready(function(){ 
    $('#MyButton').click(function(){ 
     CapacityChart(); 
    }); 
    }); 
</script> 

<input type="button" value="Capacity Chart" id="MyButton" > 
+4

D'accord. Dans de nombreux cas, jQuery et d'autres frameworks sont purement et simplement exagérés pour de petites quantités de javascript et tous les codes javascript ne doivent pas nécessairement être inter-navigateurs. –

+2

assez juste .. le point que je voulais faire était « une meilleure façon de le faire » est ... discrètement Sans jQuery, quelque chose comme: var btn = document.getElementById (« MyButton »); btn.onclick = function() {CapacityChart();} – Paul

+0

J'ai essayé mais ça ne marche pas non plus. – fmz

3

Cela semble correct. Je suppose que vous avez défini votre fonction avec un nom différent ou dans un contexte qui n'est pas visible par le bouton. Veuillez ajouter du code

1

Un problème majeur que vous avez est que vous utilisez le navigateur renifler pour aucune bonne raison:

if(navigator.appName == 'Netscape') 
    { 
     vesdiameter = document.forms['Volume'].elements['VesDiameter'].value; 
     // more stuff snipped 
    } 
    else 
    { 
     vesdiameter = eval(document.all.Volume.VesDiameter.value); 
     // more stuff snipped 
    } 

Je suis sur Chrome, donc navigator.appName aura pas Netscape. Est-ce que Chrome prend en charge document.all? Peut-être, mais peut-être pas encore. Et qu'en est-il des autres navigateurs?

La version du code sur la branche Netscape devrait fonctionner sur tous les navigateurs de retour à Netscape Navigator 2 à partir de 1996, donc vous devriez probablement rester avec ça ... sauf que ça ne marchera pas (ou n'est pas « t garanti au travail) parce que vous n'avez pas spécifié un attribut name sur les input éléments, donc ils ne seront pas ajoutés au tableau elements de la forme comme éléments nommés:

<input type="text" id="VesDiameter" value="0" size="10" onKeyUp="CalcVolume();"> 

Ou leur donner un nom et de l'utilisation le tableau elements, ou (mieux) utiliser

var vesdiameter = document.getElementById("VesDiameter").value; 

qui fonctionnera sur tous les navigateurs modernes - pas de branchement nécessaire. Juste pour être du bon côté, remplacer ce renifler pour une version du navigateur supérieur ou égal à 4 avec un chèque de soutien getElementById:

if (document.getElementById) { // NB: no brackets; we're testing for existence of the method, not executing it 
    // do stuff... 
} 

Vous voulez probablement valider votre entrée ainsi; quelque chose comme

var vesdiameter = parseFloat(document.getElementById("VesDiameter").value); 
if (isNaN(vesdiameter)) { 
    alert("Diameter should be numeric"); 
    return; 
} 

aiderait.

+0

Salut NickFitz, un de mes défis ici est que ce script a été écrit en 1993 - d'où les références à Netscape 4 J'ai eu de l'aide pour la mettre à jour et cela a fonctionné jusqu'à ce que je l'insère dans sa page. – fmz

+0

Je doute qu'il ait été écrit en 1993, car Brendan Eich n'a pas inventé JS avant 1995. http://en.wikipedia.org/wiki/Javascript#History ;-) Je vous recommande fortement d'utiliser 'document.getElementById' et de vous déshabiller l'autre truc. – NickFitz

+0

Je pense qu'il serait prudent d'au moins le faire fonctionner dans IE avant de travailler sur la compatibilité du navigateur, sinon il ne saura pas si les problèmes de compatibilité de son navigateur seront résolus, car il ne fonctionnera toujours pas. –

5

Votre code HTML et la façon dont vous appelez la fonction à partir du bouton semblent corrects.

Le problème semble être dans la fonction CapacityCount. Je reçois cette erreur dans ma console sur Firefox 3.5: "document.all est indéfini" à la ligne 759 de bendelcorp.js.

Edit:

On dirait document.all est une chose IE seule et est une façon non standard d'accès au DOM. Si vous utilisez document.getElementById(), cela devrait probablement fonctionner.Exemple: document.getElementById("RUnits").value au lieu de document.all.Capacity.RUnits.value

+0

Ce n'est pas spécifiquement le problème avec la fonction, qui ne jette aucune erreur dans IE –

1

Votre code échoue sur cette ligne:

var RUnits = Math.abs(document.all.Capacity.RUnits.value); 

i essayé bien marcher avec Firebug et il échoue là. Cela devrait vous aider à comprendre le problème.

vous avez jquery référencé. vous pourriez aussi bien l'utiliser dans toutes ces fonctions. ça nettoiera votre code de manière significative.

+0

It is ' t échouer dans IE sur cette ligne, cependant. –

+0

car document.all est une chose IE. il devrait juste utiliser $ ('# RUints'). Val() jquery notation b/c il est déjà jquery. ceci prend soin de toutes les différences de navigation et nettoie le code. – Patricia

1

Juste pour que vous sachiez, le point-virgule (;) n'est pas censé être là dans le bouton lorsque vous appelez la fonction.

Il devrait juste ressembler à ceci: onclick="CapacityChart()"

alors tout devrait fonctionner :)

0

J'ai une fonction call-support code bouton intelligent:

<br> 
<p id="demo"></p><h2>Intelligent Button:</h2><i>Note: Try pressing a key after clicking.</i><br> 
<button id="button" shiftKey="getElementById('button').innerHTML=('You're pressing shift, aren't you?')" onscroll="getElementById('button').innerHTML=('Don't Leave me!')" onkeydown="getElementById('button').innerHTML=('Why are you pressing keys?')" onmouseout="getElementById('button').innerHTML=('Whatever, it is gone.. maybe')" onmouseover="getElementById('button').innerHTML=('Something Is Hovering Over Me.. again')" onclick="getElementById('button').innerHTML=('I was clicked, I think')">Ahhhh</button> 
Questions connexes