"dynamic" databasejoin

susannanam

Member
hello all,

maybe (i hope) this is something super simple but i searched and so far did not find any solution: i have the same databasejoin for a few fields and each time, one value is selected, this value should disappear once the client clicks on the next databasejoin field.

e.g. in field 1, the options are a,b,c,d -> the client selects option b. in the next field 2, the options should now only be a,c,d...

what would be the easiest way to achieve this?

thanks for any assistance
susanna
 
There isn't a built in way of doing it, but you can do it in JS. It's not Ninja rocket surgery level coding, but it's not entirely trivial.

Basically you'd watch for a change event on each of your dropdowns, grab the selected index (or value) of the changed one, then enable/disable options on the others as appropriate.

There's a number of example solutions out there, if you google around. I seem to recall finding some useful ones on Stack Overflow last time I had to do this.

-- hugh
 
i have found a piece of code that i can use as base i think:
JavaScript:
// when all the elements in the DOM are loaded
document.addEventListener('DOMContentLoaded', function() { 
  // get both lists and their HTMLOptionElement nodes
  var list1 = document.getElementById('day_list_1'),
      list2 = document.getElementById('day_list_2'),
      options1 = list1.querySelectorAll('option'),
      options2 = list2.querySelectorAll('option');
 
  // add event handlers when the lists are changed to call the update function
  $(list1).change(update).SumoSelect();
  $(list2).change(update).SumoSelect();

  function update(e) {
    // when the lists are changed, loop through their HTMLOptionElement nodes
    var other = (list1 === this) ? list2 : list1;   
    for (var i = 0; i < options1.length; i++) {
      // options of list1 should be disabled if selected in list2 and vice-versa
      this[i].selected ? other.sumo.disableItem(i) : other[i].selected ? void 0 : other.sumo.enableItem(i);
    }
  }
});

in my form, i add a php event... but how can i now grab the change on a databasejoin-field? do you have any more hint for me Hugh?

thanks
susanna
 
Try this ...

Create a form_X.js file for your form (in ./components/com_fabrik/js, replace X with numeric form ID).

Code:
function doStates(el) {
   var els = ['fab_trip_pics___state', 'fab_trip_pics___state_2'];
   els.each(function (dd) {
      if (dd != el.element.id) {
         thisel = el.form.formElements.get(dd).element;
         jQuery(thisel.options).prop('disabled','');
         thisel.options[el.element.selectedIndex].disabled="disabled"}
   }.bind(el));
}

Replace those element names in the els array with yours. Add a JS event on each element, on change, doStates().

http://screencast.com/t/6xb7DAGh

Note that this code assumes the dropdowns are identical, so they have exactly the same options in exactly the same place. It uses the index of the selected value, not the value itself. So it only cares that you select (say) the 6th option one one dropdown, and disables the 6th option on all the others.

If your options are in a different order, you can still do it, but it gets a little more complex.

the script will work with any number of identical dropdowns, not just two.

-- hugh
 
thanks so much Hugh :) sorry but i am really really new to JS and if you say the element names... i am still not sure which one to change.. is it where it says el. ?

it is the very same dropdown field actually as i add records into a "repeated group". but each value of the dropdown field (it is actually a databasejoin) can be used only once.

thanks for all your assistance
susanna
 
There is only one line with element names in it. Where I set up the array of element names, like 'fab_trip_pics___state'. Change that to be your element names. The example just uses two, you can add more.

-- hugh
 
We are in need of some funding.
More details.

Thank you.

Members online

Back
Top