4 Replies Latest reply on Nov 18, 2011 10:06 AM by invincible_virus

    Mutiple ComboBoxes using c:forEach

    invincible_virus Newbie

      I want to create mutiple ComboBoxes from a Map containing label for the box as key and an object having [possible values, selected value] as Value (id=bundleItemDecoration).

      This map is updated on value change of another ComboBox (id=bundleType).

      Code works fine when rendered for the first time, but behaves wierd when re-rendered.

      When I change the value in ComboBox (id=bundleType), Map is updated and labels (id=bundleItemDecoration) are displayed correctly on the Page but possible values in their corresponding ComboBoxes (id=bundleItemDecoration) are not changed.

      Please help.


      <s:decorate id="bundleTypeDecoration" template="../layout/edit.xhtml">
          <ui:define name="label">Bundle Type:</ui:define>
          <rich:comboBox id="bundleType" selectFirstOnUpdate="true"
              defaultLabel="Select Bundle Type"
              <a4j:support event="onchange"
                  reRender="billingInfoDecoration, bundleItemDecoration, billingDealRender, createBundleErrors"
                  eventQueue="default" />
      <s:decorate id="bundleItemDecoration">
          <c:forEach var="bundleItem" items="#{createBundle.billingServIdDisplayNmSOList}">
              <s:decorate id="#{bundleItem.key}#{createBundle.bundleTypeSelectedCd}" template="../layout/edit.xhtml">
                  <ui:define name="label">#{bundleItem.key}:</ui:define>
                      defaultLabel="Select Service Offering"
        • 1. Re: Mutiple ComboBoxes using c:forEach
          Christian Peter Expert

          This is probably yet another buildtime vs. rendertime issue with c:forEach. Please try a4j:repeat or ui:repeat instead.

          • 2. Re: Mutiple ComboBoxes using c:forEach
            invincible_virus Newbie

            Got few links pointing to this buildtime vs rendertime issue - http://www.ninthavenue.com.au/blog/c:foreach-vs-ui:repeat-in-facelets

            Tried with a4j:repeat and ui:repeat, but the problem is even bigger with them.

            c:forEach works fine on first render but never updates on rerendering. But with a4j:repeat and ui:repeat comboboxes are not visible even on first time component rendering.

            BTW.. is 'rich:comboBox' buildtime or rendertime ?

            • 3. Re: Mutiple ComboBoxes using c:forEach
              Christian Peter Expert

              please try without the s:decorate and its constructed id and iterate with a4j:repeat or ui:repeat the rich:comboBox only:


              <a4j:outputPanel id="rerenderme">


              <a4j:repeat value="#{source}" var="item>

                   <rich:comboBox .../>





              Then rerender the outputPanel instead of the s:decorate.





              I've tried in rf 3.3.3 and even this one works fine:


                   <s:decorate id="output1">

                   <a4j:repeat value="#{demo.myList}" var="entry" rowKeyVar="ro">

                        <s:decorate id="TEST#{ro}">

                             <rich:comboBox value="#{ro}"/>





              buildtime vs. rendertime reflects here: the id TEST#{ro} is alwas "jid_xyz:j_id_abc:TEST" the #{ro} part is lost / evaluated to late.


              Maybe there is something wrong in your edit.xhtml template!

              • 4. Re: Mutiple ComboBoxes using c:forEach
                invincible_virus Newbie

                The issue is now solved. Rootcause was the usage of Map to hold the data.

                Combobox once rendered on the UI keeps refering to same data pointer e.g.




                will keep on pointing to the soSuggestionList of same key in the HashMap even if c:forEach has rerendered the UI component.


                Solution is to use List instead of map. On re-rendering the UI component, we will actually change the binding data to the suggestionValues property of rich:comboBox.


                Final working piece of code (with few more modifications) -

                <s:decorate id="billingDealRender">

                    <h:panelGroup rendered="#{createBundle.showBillingDetails}">


                            <s:decorate id="billingDeal1" template="../layout/edit.xhtml">

                                <ui:define name="label">Billing Deal:</ui:define>


                                <rich:comboBox id="billingDeal" selectFirstOnUpdate="true"



                                    defaultLabel="Select Billing Deal"





                                <a4j:support event="onselect" ajaxSingle="true"


                                    eventQueue="default" />



                            <br class="clear" />





                P.S. Thanks to Peter for the help.