Précédent   Forum des professionnels en informatique > Webmasters - Développement Web > JavaScript
JavaScript Forum programmation JavaScript. Lire : Cours JavaScript, FAQ JavaScript, Toutes les FAQ JavaScript et Sources JavaScript
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse Proposer ce sujet en actualité
 
Outils de la discussion
Publicité
'
Vieux 15/07/2011, 12h42   #1
Invité de passage
 
Inscription : février 2010
Messages : 5
Détails du profil
Informations forums :
Inscription : février 2010
Messages : 5
Points : 0
Points : 0
Par défaut limiter les réponses pour un QCM

Bonjour à tous !

Plus que débutant, je travail via le logiciel eXelearning à l'élaboration de cours QCM et autre moyen pédagogique pour un centre de formation. Le logiciel génère du code html et javascript.
Je souhaiterais vérouiller le nombre de réponse possible lors des tests de controle.
Je m'explique, lors d'un QCM par exemple on peut cocher les case à plusieur reprise jusqu'à obtenir la bonne réponse. Peut grace à java, n'autoriser qu'une seule action ?

Merci de vos avis et reponses.
debutant75013 est déconnecté   Envoyer un message privé Réponse avec citation 02
Vieux 15/07/2011, 14h49   #2
Membre Expert
 
Avatar de Watilin
 
Homme Matilin Torre
Étudiant
Inscription : juin 2010
Messages : 679
Détails du profil
Informations personnelles :
Nom : Homme Matilin Torre
Âge : 23
Localisation : France, Ille et Vilaine (Bretagne)

Informations professionnelles :
Activité : Étudiant

Informations forums :
Inscription : juin 2010
Messages : 679
Points : 1 202
Points : 1 202
Je mets -1 pour le titre de topic qui sert à rien, et parce que c'est JavaScript, pas Java.

Pour ton problème, comment souvent, il y a plusieurs façons de faire. Une est simple mais fastidieuse, car il faut rajouter un attribut dans le code HTML de chaque bouton radio. Une autre, reposant sur la délégation d'évènements, serait plus élégante mais plus complexe. Je te propose la première.

Je commence par créer une fonction qui va désactiver tous les boutons de même nom :
Code JS :
1
2
3
4
5
6
7
function desactiver( nom ) {
   var boutons = document.getElementsByName(nom);
   var length = boutons.length;
   for (var i = 0; i < length; i++) {
      boutons[i].disabled = true;
   }
}

Ensuite, il faudra rajouter un appel à cette fonction sur chaque bouton radio :
Code HTML :
<input type="radio" ... onclick="desactiver(this.name);" />

Si tu te sens d'attaque pour la solution « plus élégante », y'a qu'à demander

Autre chose : je sais, de ma propre expérience, que le e-learning se soucie parfois peu de la sécurité des questionnaires. Mais il faut que tu saches qu'une vérification côté client n'est pas suffisante. Par exemple, avec une console JavaScript (il y en a dans tous les navigateurs actuels), il suffit de taper un tout petit bout de code pour casser la protection que je viens de te donner.

L'idéal serait de faire une requête auprès du serveur (avec ou sans Ajax) quand l'utilisateur propose une réponse, et de s'assurer, côté serveur, qu'il ne pourra pas proposer une autre réponse par la suite.

__________________
Disposition de clavier ergonomique française : Bépo
Watilin est déconnecté   Envoyer un message privé Réponse avec citation 10
Vieux 15/07/2011, 15h18   #3
Invité de passage
 
Inscription : février 2010
Messages : 5
Détails du profil
Informations forums :
Inscription : février 2010
Messages : 5
Points : 0
Points : 0
Merci beaucoup de ces precieuses informations.

Je suis partant pour la solution "elegante"
manière de tester tout ça.

Merci aussi pour l'astuce de securité. Je n'y avait effectivement pas pensé.
debutant75013 est déconnecté   Envoyer un message privé Réponse avec citation 10
Vieux 15/07/2011, 17h03   #4
Membre Expert
 
Avatar de Watilin
 
Homme Matilin Torre
Étudiant
Inscription : juin 2010
Messages : 679
Détails du profil
Informations personnelles :
Nom : Homme Matilin Torre
Âge : 23
Localisation : France, Ille et Vilaine (Bretagne)

Informations professionnelles :
Activité : Étudiant

Informations forums :
Inscription : juin 2010
Messages : 679
Points : 1 202
Points : 1 202
Pour la seconde solution,
l'idée c'est d'utiliser un gestionnaire d'évènement addEventListener, en surveillant non pas chaque input, mais le formulaire qui les contient tous. C'est ça qu'on appelle la délégation.
Pour que ça marche, il faut qu'il y ait dans le code HTML au moins le <form> et les <input>, mais je te mets des balises en bonus pour améliorer la sémantique et l'accessibilité.
Code HTML :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
<form method="post" action="" id="questionnaire">
	...
	<fieldset>
		<legend>Question 2</legend>
		<input type="radio" name="q2" id="q2A" />
		<label for="q2A">réponse A</label>
		<input type="radio" name="q2" id="q2B" />
		<label for="q2B">réponse B</label>
		<input type="radio" name="q2" id="q2C" />
		<label for="q2C">réponse C</label>
		<input type="radio" name="q2" id="q2D" />
		<label for="q2D">réponse D</label>
	</fieldset>
	<fieldset>
		<legend>Question 3</legend>
		<input type="radio" name="q3" id="q3A" />
		<label for="q3A">réponse A</label>
		<input type="radio" name="q3" id="q3B" />
		<label for="q3B">réponse B</label>
		<input type="radio" name="q3" id="q3C" />
		<label for="q3C">réponse C</label>
		<input type="radio" name="q3" id="q3D" />
		<label for="q3D">réponse D</label>
	</fieldset>
	...
</form>

La fonction en elle-même est très courte, et tu reconnaîtras une partie commune avec la première solution :
Code JS :
1
2
3
4
5
6
7
8
9
10
11
function gererClic( e ) {
   var target = e.target || e.srcElement;
   if ('INPUT' == target.tagName && 'radio' == target.type) {
      var nom = target.name;
      var boutons = document.getElementsByName(nom);
      var length = boutons.length;
      for (var i = 0; i < length; i++) {
         boutons[i].disabled = true;
      }
   }
}
La ligne 2 permet de récupérer la cible réelle du clic. D'habitude on utilise this, mais comme le gestionnaire sera attaché au formulaire, this correspond au formulaire et ce n'est pas ce qu'on veut. e.target fonctionne avec les navigateurs qui respectent le standard, et e.srcElement marche sous IE<9.

De même, il faut prendre en compte IE<9 au moment d'attacher le gestionnaire :
Code JS :
1
2
3
4
5
if (window.addEventListener) { // standard
   document.getElementById('questionnaire').addEventListener('click', gererClic, false);
} else { // IE<9
   document.getElementById('questionnaire').attachEvent('onclick', gererClic);
}

Note le 3e paramètre false de la méthode standard, qui ne sert (presque) à rien mais qui est obligatoire

Le gros avantage de cette méthode, c'est que le script n'est plus intrusif : il n'apparaît plus du tout dans le code HTML, ce qui rend la maintenance plus facile. C'est le même principe que déclarer les styles dans une feuille CSS externe.
Pour faire les choses bien jusqu'au bout, on déclare les scripts dans le <head>. Mais ça pose un problème : au moment où les scripts sont exécutés, le contenu de la page n'existe pas encore… Pour pallier ce problème, on retarde l'exécution des scripts, en les plaçant dans un gestionnaire de l'évènement load de la page.

Voilà ce que ça donne au final, si on place le code dans le <head> :
Code JS :
1
2
3
4
5
6
7
8
9
10
11
12
13
function gererClic( e ) {
   ... // cf. au-dessus
}
 
if (window.addEventListener) { // standard
   window.addEventListener('load', function() {
      document.getElementById('questionnaire').addEventListener('click', gererClic, false);
   }, false);
} else { // IE<9
   window.attachEvent('onload', function() {
      document.getElementById('questionnaire').attachEvent('onclick', gererClic);
   });
}
__________________
Disposition de clavier ergonomique française : Bépo
Watilin est déconnecté   Envoyer un message privé Réponse avec citation 20
Vieux 15/07/2011, 21h49   #5
Expert Confirmé Sénior
 
Avatar de RomainVALERI
 
Homme Romain VALERI
POOête
Inscription : avril 2008
Messages : 2 572
Détails du profil
Informations personnelles :
Nom : Homme Romain VALERI
Âge : 35
Localisation : France, Meurthe et Moselle (Lorraine)

Informations professionnelles :
Activité : POOête

Informations forums :
Inscription : avril 2008
Messages : 2 572
Points : 4 074
Points : 4 074
Citation:
Envoyé par Watilin
<solution élégante>
Un tutoriel complet à la demande... techniquement exact, bien écrit, avec code à l'appui...

>>> Watilin for President !
__________________

...pour les linguistes et les curieux >>> générateur de phrases aléatoires

__________________
RomainVALERI est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 15/07/2011, 21h52   #6
Modérateur
 
Avatar de NoSmoking
 
Homme
Inscription : janvier 2011
Messages : 2 942
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Isère (Rhône Alpes)

Informations forums :
Inscription : janvier 2011
Messages : 2 942
Points : 4 768
Points : 4 768
Très belle explication +1
il me semble qu'il manque e = e || event;en début de fonction gererClic au cas ou l'event ne soit pas passé à la fonction.
NoSmoking est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Vieux 16/07/2011, 14h38   #7
Membre Expert
 
Avatar de Watilin
 
Homme Matilin Torre
Étudiant
Inscription : juin 2010
Messages : 679
Détails du profil
Informations personnelles :
Nom : Homme Matilin Torre
Âge : 23
Localisation : France, Ille et Vilaine (Bretagne)

Informations professionnelles :
Activité : Étudiant

Informations forums :
Inscription : juin 2010
Messages : 679
Points : 1 202
Points : 1 202
Arrêtez je vais prendre la grosse tête '^^
Citation:
Envoyé par NoSmoking Voir le message
il me semble qu'il manque e = e || event;en début de fonction gererClic au cas ou l'event ne soit pas passé à la fonction.
De mémoire, le seul cas où l'event n'est pas passé, c'est sous IE quand on utilise les propriétés « DOM 0 » on..., par exemple window.onload. En tout cas, avec attachEvent ça ne pose pas de problème.
__________________
Disposition de clavier ergonomique française : Bépo
Watilin est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 16/07/2011, 15h59   #8
Modérateur
 
Avatar de NoSmoking
 
Homme
Inscription : janvier 2011
Messages : 2 942
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Isère (Rhône Alpes)

Informations forums :
Inscription : janvier 2011
Messages : 2 942
Points : 4 768
Points : 4 768
Citation:
Envoyé par Watilin Voir le message
De mémoire, le seul cas où l'event n'est pas passé, c'est sous IE quand on utilise les propriétés « DOM 0 » on..., par exemple window.onload. En tout cas, avec attachEvent ça ne pose pas de problème.
c'est tout à fait vrai, c'est simplement que dans le cas d'une réutilisation de ta fonction en l'affectant, justement, directement sur le onclick d'un objet cela plantera.

Ceci devient de plus en plus fréquent lorsque l'on met l'initialisation en fin de page, pour être sur que les éléments sont présent dans le DOM et éviter les attachEvent et addEventListener, c'est pour cela que j'ai tendance à le mettre systématiquement.

Citation:
Envoyé par Watilin Voir le message
Arrêtez je vais prendre la grosse tête '^^
mais non, cela vaut quand même bien une
NoSmoking est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Réponse Proposer ce sujet en actualité
Outils de la discussion



Fuseau horaire GMT +2. Il est actuellement 22h04.


 
 
 
 
Partenaires

Hébergement Web