Pandi: jQuery required setzen bei select Auswahl

Hallo,

folgende Ausgangssituation

<form form method="post">

	<label for="autoStart">Automatisch starten?</label>
	<input name="autoStart" type="radio" value="Ja" checked="" /> Ja 
	<input name="autoStart" type="radio" value="Nein"/> Nein

	<label for="f1">Feld 1*</label>
	<select name=f1"" id="f1" required="">
		<option value="">-- Bitte wählen --</option>
		<option value="f1-1">Eintrag 1 - Feld 1</option>
		<option value="f1-2">Eintrag 2 - Feld 1</option>
		<option value="f1-3">Eintrag 3 - Feld 1</option>
	</select>

	<label for="f2">Feld 2*</label>
	<select name="f2" id="f2" required="">
		<option value="">-- Bitte wählen --</option>
		<option value="f2-1">Eintrag 1 - Feld 2</option>
		<option value="f2-2">Eintrag 2 - Feld 2</option>
		<option value="f2-3">Eintrag 3 - Feld 2</option>
	</select>

	<button id="eintragen">Speichern</button>

</form>



<script src="jquery311min.js"></script>

<script> 
	$(document).ready(function(){

		$(':radio[name=autoStart]').click(function(){
			    
			    if($(this).val() == 'Ja'){
			        $("#f1").prop('required',true);
			        $("#f2").prop('required',true);
			    } else {
			    	$("#f1").prop('required',false);
			        $("#f2").prop('required',false);
			    }
			
			});

	});              
</script>

Wenn Automatisch starten? auf ja steht, sind die Felder #f1 und #f2 auf required. Lege ich den Schalter auf Nein, werden diese entfernt, klappt.

Jetzt kommt die Schwierigkeit:
Wenn in #f1 oder #f2 etwas gewählt wird, dann sollte im anderen Feld das required wieder entfernt werden.

Beispiel:

Automatisch Starten: Ja Feld 1: Etwas gewählt Feld 2: ist kein required mehr.

Wenn ich ausversehen im Feld 1 <option value="">-- Bitte wählen --</option> wähle. soll natürlich das required wieder aktiviert werden und zwar in beiden Feldern.

Wie könnte ich dieses angehen? Habt ihr eine Lösung / Idee?

  1. Tach!

    Wie könnte ich dieses angehen? Habt ihr eine Lösung / Idee?

    Du kannst dir zunächst erstmal sowas wie eine Wahrheitstabelle erstellen. Wenn es zwei Beteiligte gibt (A und B), die jeweils zwei Zustände haben können, dann gibt es vier Möglichkeiten der Kombination.

    A | B | Was soll passieren? Zustand 1 | Zustand 1 Zustand 2 | Zustand 1 Zustand 1 | Zustand 2 Zustand 2 | Zustand 2

    Die Formel dazu lautet Anzahl der Zustände hoch Anzahl der Beteiligten. Bei drei Beteiligten sind es 8 Zustände, und so weiter. In einem solchen Fall muss die Tabelle größer werden.

    Wenn ich das richtig sehe, ist das mit zwei Beteiligten und zwei Zuständen bei dir der Fall. Die beiden Zustände lauten "nichts gewählt" und "irgendwas anderes gewählt" und die Beteiligten sind #f1 und #f2.

    Mit der Tabelle gehst du sicher, dass du keine der möglichen Zustandskombinationen übersiehst. Und nun füllst du die dritte Spalte aus. Anschließend formulierst du das in Code, zum Beispiel mit if-else-Kombinationen.

    dedlfix.

    1. Hallo,

      vielen Dank für dein Erklärung. Wenn ich dich richtig verstanden habe, dann in etwa so?

      $(document).ready(function(){
      
      		$(':radio[name=autoStart]').click(function(){
      			    
      			    if($(this).val() == 'Ja'){
      			        $("#f1").prop('required',true);
      			        $("#f2").prop('required',true);
      			    
      			    } else {
      			    	
      			    	$("#f1").prop('required',false);
      			        $("#f2").prop('required',false);
      			    }
      			});
      
      		$('#f1').change(function(){
      			    
      			    if($(this).val() !== ''){
      			        $("#f2").prop('required',false);
      			    }
      
      			
      			});
      	});         
      
      1. Tach!

        vielen Dank für dein Erklärung. Wenn ich dich richtig verstanden habe, dann in etwa so?

        Durchaus. Ich prüf das jetzt aber nicht. Du weißt, dass du es richtig gemacht hast, wenn du alle vier Zustände probierst und dabei jeweils das erwartete Ergebnis herauskommt.

        dedlfix.

  2. Edit: Ich habe VOR 13:13 Uhr angefangen zu schreiben 😉


    Ich denke, was du suchst, ist das change-Event.

    $("select").change(function(evt) {
       var otherId = this.Id === "f1" ? "#f2" : "#f1";
       $(otherId).prop("required", this.selectedIndex === 0);
    
    });
    

    Der Change-Handler schaut sich die ID des Select an, für das er aufgerufen wurde, und ermittelt daraus die ID des Partner-Select. Bei 2 Selects geht das so einfach, wenn Du mehr hast, wird das größer (bzw. man braucht eine abstraktere Lösung).

    An diesem anderen Select wird das required-Property gesetzt, und zwar auf true, wenn der eigene selectedIndex gleich 0 ist (entspricht dem "Bitte wählen") und sonst auf false.

    Könnte schon reichen...

    Zum Radio-Button hätte ich auch noch Anmerkungen…

    • :radio ist eine jQuery-Extension und langsam. input[type=radio] kann mit querySelectorAll verarbeitet werden und ist damit schneller.
    • Du solltest jeden Radio-Button einzeln in ein Label setzen, damit der Klick auf den Text "Ja" oder "Nein" ebenfalls den Radiobutton umstellt. Also so:
    Automatisch starten?
    <label><input name='autoStart' type='radio' value='Ja' /> Ja</label>
    <label><input name='autoStart' type='radio' value='Nein' /> Nein</label>
    
    • Dein Click-Hander für die Radiobuttons lässt sich deutlich kompakter schreiben, jQuery kann mehr als ein Objekt selektieren und führt die angegebene Methode für alle Objekte im matched set aus. Und Codemuster der Art if (bedingung) func(true) else func(false) sind unnötig, das schreibt man kürzer als func(bedingung). Damit fällt dein Click-Handler zu dem hier ineinander:
    $('input[type=radio][name=autoStart]').click(function(evt) {
       $('select').prop('required', this.Value === 'Ja');
    });
    

    Rolf

    1. @@Rolf b

      • :radio ist eine jQuery-Extension und langsam. input[type=radio] kann mit querySelectorAll verarbeitet werden und ist damit schneller.

      Es gibt schon eine Collection der Eingabefelder, die muss man nicht nochmals im ganzen DOM suchen. Mit document.forms[0].elements['autoStart'] hat man die Gruppe der Radiobuttons (wenn sie denn im ersten Formular auf der Seite sind; wenn das Formular einen Namen hat, kann man den auch gern anstatt der 0 verwenden).

      $('input[type=radio][name=autoStart]').click(function(evt) {
      

      Warum so spezifisch? $('[name=autoStart]') sollte genügen. Aber s.o.

      LLAP 🖖

      --
      “When UX doesn’t consider all users, shouldn’t it be known as ‘Some User Experience’ or... SUX? #a11y” —Billy Gregory
      1. Wieder was gelernt - ich war im Glauben, man müsste damit eindeutige Elemente ansprechen.

        Wegen der überspezifischen Angaben: Ich weiß, das wird schräg angeschaut. Aber ich bin lieber zu genau als dass ich irgendwas treffe, was ich nicht will.

        Aber da sich Elemente als Property im Form manifestieren, kann man es auch so formulieren und die Suche nach den gewünschten Elementen optimieren. Hätte das Form auch einen Namen, könnte man den auch als Attribut nutzen (das war in HTML 4 deprecated und ist es in HTML 5 nicht mehr, wenn ich das richtig verstanden habe).

        $(document.forms[0].autoStart).click(...);
        

        Rolf

      2. Moin,

        Darf ich dazu noch bemerken das alternativ noch getElementsByName zum Einsatz kommen könnte und dass die direkten DOM Methoden unter Umständen viel schneller sind als jQuery-Selectionen via css name-Attribut-Selector. GetElementsByName vs. JQuery

        Gruß Bobby

        --
        -> Für jedes Problem gibt es eine Lösung, die einfach, sauber und falsch ist! <- ### Henry L. Mencken ### -> Nicht das Problem macht die Schwierigkeiten, sondern unsere Sichtweise! <- ### Viktor Frankl ### ie:{ br:> fl:{ va:} ls:< fo:) rl:( n4:( de:> ss:) ch:? js:( mo:} sh:) zu:)
  3. @@Pandi

    <form form method="post">
    
    	<label for="autoStart">Automatisch starten?</label>
    	<input name="autoStart" type="radio" value="Ja" checked="" /> Ja 
    	<input name="autoStart" type="radio" value="Nein"/> Nein
    

    Hier stimmt dein Markup nicht. Zunächst einmal hat das form-Element kein form-Attribut.

    Das Label ist keinem Eingabefeld zugeordnet. Das for-Attribut bezieht sich auf die ID eines Elements; ein Element mit der ID autoStart gibt es aber nicht.

    Die Label für die Radiobuttons wären auch „Ja“ und „Nein“.

    Eine Gruppe von Radiobuttons sollte in einem fieldset-Element eingeschlossen sein. „Automatisch starten?“ wäre der Inhalt des legend-Elements.

    Sieht dann so aus:

    <form method="post">
    
    	<fieldset>
    		<legend>Automatisch starten?</legend>
    		<input name="autoStart" id="autoStart-ja" type="radio" value="Ja" checked="" />
    		<label for="autoStart-ja">Ja</label>
    		<input name="autoStart" id="autoStart-nein" type="radio" value="Nein"/>
    		<label for="autoStart-nein">Nein</label>
    	</fieldset>
    

    	<label for="f1">Feld 1*</label>
    	<select name=f1"" id="f1" required="">
    

    Hier ist die Zuordnung Label – Eingabefeld korrekt.

    Die Anführungszeichen allerdings nicht.

    LLAP 🖖

    --
    “When UX doesn’t consider all users, shouldn’t it be known as ‘Some User Experience’ or... SUX? #a11y” —Billy Gregory