Close all expanded rows inside a ui:repeat

偶尔善良 提交于 2019-12-23 03:26:34

问题


I have a ui:repeat of auction items inside a table. It is a regular html table because when you click on a Bid commandLink a row opens right under the selected auction item, and displays a bidding component. The Bid commandLink is using ajax like this:

<f:ajax listener="#{bean.addBidView(lot)}" render="bidView" />

addBidView is updating a map of auctionItems and that's how the correct selected row opens up. When the user clicks on the same Bid link again, the addBidView figures it out and closes the bidding component.

Now let's say the user clicks on several rows, and thus opens several bidding components. They all open, but only one is active. So here's my question: how do I get the entire loop to render when I use the above ajax, so that opening a bidding component would automatically close the other open ones. (the auction items map is reflecting the correct bidding component, but only this one bidding area is rendered, so the others aren't effected. If I'm refreshing the whole page, the display is correct, and the problem only exists when I'm using ajax.)

This is the structure of the elements on the page (all this is inside an h:form:)

<table id="bidstable">
    <h:panelGroup id="entireLoop">
        <ui:repeat id="repeatAuctionItems" var="auctionItem" varStatus="status" value="#{bean.auctionItems}">
            <td>... a bunch of td's with the auction item values ... and then: 
                <h:commandLink id="bid" rendered="#{some conditions}">
                    <f:ajax listener="#{bean.addBidView(auctionItem)}" render="bidView"/>
                </h:commandLink>
            </td>
        </ui:repeat>
    </h:panelGroup>
</table>

I tried pretty much every combination of elements in the "render" -- for example:

render="bidView bidsTable"

or render="bidView bidsTable:entireLoop:repeateAuctionItems"

and every other trail I can think of. Nothing works. Any ideas?


回答1:


You have specified a client ID in the <f:ajax render> attribute which is relative to the current NamingContainer component. Client IDs which do not start with the naming container separator character, which defaults to :, are relative to the current NamingContainer component. The <ui:repeat> is such a component. So the client ID has to refer a child of <ui:repeat>. But the component which you are trying to reference is actually outside the <ui:repeat>. You'd need to reference it with an absolute client ID instead.

To find the absolute client ID, you need to open the page in the browser, rightclick and do View Source and then locate the generated HTML of the closest parent JSF component outside <ui:repeat>, which is in your particular case the <h:panelGroup id="entireLoop">. It'll look something like:

<span id="someId:possiblyOtherId:entireLoop">

Take exactly this client ID and prefix it with : for usage in <f:ajax render>.

<f:ajax ... render=":someId:possiblyOtherId:entireLoop" />

If it contains a dynamically generated ID like j_id_123, then you'd need to give all parent NamingContainer components like <h:form> a fixed ID like <h:form id="someId">.

Note that it is not possible to reference the client ID of a plain HTML element like <table id="bidsTable">. It has to be a fullworthy JSF component like <h:dataTable id="bidsTable">.



来源:https://stackoverflow.com/questions/9466977/close-all-expanded-rows-inside-a-uirepeat

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!