We launched new forums in March 2019—join us there. In a hurry for help with your website? Get Help Now!
    • 35756
    • 166 Posts
    Hello again!

    I'm still having another problem with the FormIt-validation.

    Inside my form I have three text-inputs that get validated as they should. Additionally I have two li's, each containing some checkboxes that get dynamically created.

    [[!FormItRetriever? ]]
    [[!FormIt?
    &customValidators=`check`
    &store=`1`
    &hooks=`spam,form2session,email,redirect`
    &emailTpl=`MailTpl`
    &emailTo=`[email protected]`
    &emailFromName=`[[+name]]`
    &emailSubject=`SUBJECT`
    &redirectTo=`90`
    &emailMultiSeparator=`<br />`
    &validate=`name:required,
    kurse:check:required,
    events:check:required,
    telefon:required,
    email:required`]] 


    The values of those checkboxes in the li-elements get separately stored in two hidden input-fields:

    <input type="hidden" name="kurse" value="[[+fi.kurse]]" />
    <input type="hidden" name="events" value="[[+fi.events]]" />


    What I want to achieve now is that the FormIt-validation checks for both checkbox-lists, but only one of them needs to be checked. So if one checkbox of the "kurse"-list is checked, all is fine...and if one of the "events"-list is checked, all is fine too. Right now the FormIt-validation checks them separately and provides an error if in any of the lists no checkbox is chosen/checked.

    I read about customhooks and custom validators, but I can't find any way to combine these two inputs together...as far as I understood the custom validators thing I can only check the value of the related field; and only possible results are ture or false...

    Any solution on that available?

    This question has been answered by Bruno17. See the first response.

    [ed. note: profilneurotiker last edited this post 9 years, 9 months ago.]
      • 35756
      • 166 Posts
      I'm still struggling with this...

      The FormIt-call:

      [[!FormItRetriever? ]]
      [[!FormIt?
      &customValidators=`Check-Name,Check-Email,Check-Telefon,Check-Kurs-Event`
      &store=`1`
      &hooks=`spam,form2session,email,redirect`
      &emailTpl=`MailTpl`
      &emailTo=`[email protected]`
      &emailFromName=`[[+name]]`
      &emailSubject=`SUBJECT`
      &redirectTo=`90`
      &emailMultiSeparator=`<br />`
      &validate=`name:Check-Name:required,
      telefon:Check-Telefon:required,
      email:Check-Email:required`]] 


      The form2session-hook stores all input-values. The customValidators "Check-Name" etc. are because of the prefilled input-text-fields I use in the form itself (checks if the value is not the prefilled text):

      <form class="anmeldeformular erweitert" action="[[~[[*id]]]]#anmeldung" method="post" class="form">
      
      <input type="hidden" name="kurse" value="" />
      <input type="hidden" name="events" value="" />
      
      <h2>Kurse</h2>
      <ul>
      [[!getResources? &parents=`16` &tpl=`ANMELDUNG-ERWEITERT` &showHidden=`1` &includeContent=`1` &includeTVs=`1` &processTVs=`1` &tvFilters=`ANMELDUNG==%1%` &limit=`100`]]
      </ul>
      
      
      <h2>Events</h2>
      <ul class="events">
      [[!getResources? &parents=`4` &tpl=`ANMELDUNG-ERWEITERT-EVENTS` &showHidden=`1` &includeContent=`1` &includeTVs=`1` &processTVs=`1` &tvFilters=`ANMELDUNG==%1%` &limit=`100`]]
      </ul>
      
      <div class="clear"> </div>
      <a id="anmeldung"></a>
       
      <input type="text" name="name" id="name" value="[[!+fi.name:empty=`Dein Name`]]" [[!+fi.error.name:notempty=`class="error"`]] onfocus="this.value='';" onblur="if (this.value=='') this.value='Dein Name';" />
      <br />
      
      <input type="text" name="telefon" id="telefon" value="[[!+fi.telefon:empty=`Deine Telefonnummer`]]" [[!+fi.error.telefon:notempty=`class="error"`]] onfocus="this.value='';" onblur="if (this.value=='') this.value='Deine Telefonnummer';" />
      <br />
      
      <input type="text" name="email" id="email" value="[[!+fi.email:empty=`Deine Email-Adresse`]]" [[!+fi.error.email:notempty=`class="error"`]] onfocus="this.value='';" onblur="if (this.value=='') this.value='Deine Email-Adresse';" />
       
          <br class="clear" />
       
          <div class="form-buttons">
              <input type="submit" value="> FÜR AUSGEWÄHLTE KURSE ANMELDEN" />
          </div>
      </form>


      As you can see the two ul's get populated by a getResources-call, the chunks are looking like this:

      <li [[!+fi.error.kurse:notempty=`class="error"`]] >
      <input type="checkbox" name="kurse[]" value="[[+tv.Uhrzeit]] | [[getResourceField ? &id=`[[+parent]]` &field=`pagetitle`]] | [[+pagetitle]]" [[!+fi.kurse:FormItIsChecked=`[[+tv.Uhrzeit]] | [[getResourceField ? &id=`[[+parent]]` &field=`pagetitle`]] | [[+pagetitle]]`]] />
      
      <a href="./index/kurse/[[getResourceField? &id=`[[+id]]` &field=`alias`]].html" title="[[+pagetitle]]`? &id=`[[+id]]` &field=`alias`]]">[[+pagetitle]]</a>
      
      <span class="tag [[getResourceField ? &id=`[[+parent]]` &field=`pagetitle`]]">[[getResourceField ? &id=`[[+parent]]` &field=`pagetitle`]]</span>
      <span class="zeit">[[+tv.Uhrzeit]]</span>
      <span class="information">[[+description]]</span>
      </li>


      Same for the other chunk, only "kurse" get's replaed by "events" and some other spans...but that's all working fine.


      The HTML-output of the first chunk looks like this:

      <ul>
      <li>
      <input type="checkbox" name="kurse[]" value="20:15-21:45 Uhr | Montag | Yoga for the core" />
      
      <a href="./index/kurse/yoga-core.html" title="Yoga for the core">Yoga for the core</a>
      
      <span class="tag Montag">Montag</span>
      <span class="zeit">20:15-21:45 Uhr</span>
      <span class="information">für Intermediate und Advanced</span>
      
      </li>
      <li>
      <input type="checkbox" name="kurse[]" value="18:45-19:45 Uhr | Dienstag | Pilates" />
      
      <a href="./index/kurse/pilates.html" title="Pilates">Pilates</a>
      
      <span class="tag Dienstag">Dienstag</span>
      <span class="zeit">18:45-19:45 Uhr</span>
      <span class="information">für Beginner bis Advanced</span>
      
      </li>
      
      </ul>


      The html-ouput of the second chunk like this (only one example-event created so far):

      <ul class="events">
      <li  >
      <input type="checkbox" name="events[]" value="17. Mai 2014 - 18. Mai 2014 | Ort der Veranstaltung | Beispiel Event" />
      
      <a href="./index/events/beispiel-event.html" title="Beispiel Event">Beispiel Event</a>
      <span class="datum">17. Mai 2014 - 18. Mai 2014</span>
      <span class="ort">Ort der Veranstaltung</span>
      <span class="beschreibung">für Einsteiger</span>
      </li>
      </ul>


      which looks good for me too.

      So now I want the form to succeed the validation if one checkbox of both lists is chosen.

      By using this in the FormIt-call

      &validate=`
      kurse:required,
      events:required
      ...
      `


      the two lists get checked separately, which is not the way I want it to be.

      So I tried to make a custom validator on my own, which didn't work. Then I found this thread in the german-speaking area:

      http://de.modx.com/forum/thread/6360/formit-custom-validator-zugriff-auf-formularfelder

      There is an example of a customValidator and a check-snippet given, which I tried to edit for my form:

      Check-lists-snippet

      $allFormFields = $hook->getValues();
       
      switch ($allFormFields['kurse']) {
       
      case 'post': 
       
          $success = true;
          print_r($success);
          if ($allFormFields['kurse'] == '') {
              $success = false;
              $hook->addError('kurse', 'Bitte einen Kurs oder Event auswählen.'); // Fehlermeldung
          }
          if ($allFormFields['events'] == '') {
              $success = false;
              $hook->addError('events', 'Bitte einen Kurs oder Event auswählen.'); // Fehlermeldung
          }
          return $success;
          break;
      }


      I'm not quite sure what to use for this line:

      Original:

      switch ($allFormFields['whichoption']) {


      So I tried "kurse" and "events"...

      switch ($allFormFields['kurse']) {




      I edited my FormItCall like this:

      [[!FormItRetriever? ]]
      [[!FormIt?
      &customValidators=`Check-lists,Check-Name,Check-Email,Check-Telefon,Check-Kurs-Event`
      &store=`1`
      &hooks=`spam,form2session,email,redirect`
      &emailTpl=`MailTpl`
      &emailTo=`[email protected]`
      &emailFromName=`[[+name]]`
      &emailSubject=`SUBJECT`
      &redirectTo=`90`
      &emailMultiSeparator=`<br />`
      &validate=`name:Check-Name:required,
      telefon:Check-Telefon:required,
      email:Check-Email:required`]] 


      But this validates the form even without having checked a single checkbox of the lists. Also I don't get an error (li is coloured red on error by css) for any of the both lists. So if I fill the three input-text-fields that are required for validation the form-submit is interpreted as OK, it seems the Check-Lists-customValidator doesn't do anything.

      Any hint what I am missing here?
        • 3749
        • 24,544 Posts
        It might be easier to just check those two fields in JavaScript. Then, do a popup and prevent submission if they're not correct.
          Did I help you? Buy me a beer
          Get my Book: MODX:The Official Guide
          MODX info for everyone: http://bobsguides.com/modx.html
          My MODX Extras
          Bob's Guides is now hosted at A2 MODX Hosting
        • discuss.answer
          • 4172
          • 5,888 Posts
          you can try this (untested)

          snippet 'oneIsRequired'

          <?php
          
          $fields = $modx->getOption('fields',$scriptProperties,'');
          $fields = explode(',',$fields);
          
          $success = false;
          
          foreach ($fields as $field){
              $fieldrequest = $modx->getOption($field,$_REQUEST,'');
              if (!empty($fieldrequest)){
                  $success = true;
              }
          }
          
          $validations = '';
          
          if (!$success){
              foreach ($fields as $field){
                  $validations .= $field . ':required,';    
              }
          }
          
          return $validations;
          


          [[!FormIt?
          &customValidators=`Check-lists,Check-Name,Check-Email,Check-Telefon`
          &store=`1`
          &hooks=`spam,form2session,email,redirect`
          &emailTpl=`MailTpl`
          &emailTo=`[email protected]`
          &emailFromName=`[[+name]]`
          &emailSubject=`SUBJECT`
          &redirectTo=`90`
          &emailMultiSeparator=`<br />`
          &validate=`[[!oneIsRequired? &fields=`kurse,events`]]name:Check-Name:required,
          telefon:Check-Telefon:required,
          email:Check-Email:required`]]
          


          this should add required-validations for both fields, only if none of both was checked. [ed. note: Bruno17 last edited this post 9 years, 9 months ago.]
            -------------------------------

            you can buy me a beer, if you like MIGX

            http://webcmsolutions.de/migx.html

            Thanks!
            • 35756
            • 166 Posts
            Wow Bruno!

            This worked like a charm immediately!

            You deserve a donation! Next time I'll get payed you're gonna get something from me!

            Dickes Dankeschön!
              • 35756
              • 166 Posts
              After I finished my form the customer needed a select-field to be added to each li-entry, so the user can choose an option.

              I managed it by using Javascript that the chosen option gets added to a hidden input-field, which contains already some data prefilled by using placeholders. The chosen option-value gets added after the prefilled-placeholder-values.

              So I see my list, choose an option, then I want to submit the form.

              If all validations are successful a confirmation-message gets sent, but the added option-value is missing.

              I tested the form a lot and I realized, that if the validation is not successfull and the site doesn't redirect to add the missing infos, then I add the missing infos and submit the form again. This time the option-values get added in the confirmation-mail.

              So the option-values do not get added directly by choosing them, they only get "stored" if the validation is not successfull and the form needs to be send again. This only counts for options that have been chosen before the first submit! If I add some options after first submit and validation-error, only the option-values I added before the first click get transmitted in the confirmation-mail.

              So how can I define that the chosen option-values get added immediately and transmitted on first submit?