PrimeFaces中用jQuery获取AccordionPanel折叠面板激活标签ID及自动保存
Hey there! Let's tackle your problem step by step. First, we'll fix the issue of getting the correct AccordionPanel tab and hidden field when an input changes, then we'll go over solid auto-save solutions for PrimeFaces.
Fixing the Field Change Detection & Hidden Field Update
Your current jQuery code targets #reviewHidden directly, which won't work well if you have multiple tabs (it'll update all matching hidden fields). Instead, we need to traverse the DOM from the changed input to find its parent tab and corresponding hidden field.
Modified XHTML (keeping your core structure)
<p:accordionPanel id="FacilityAccordId" activeIndex="null" dynamic="true"> <p:ajax event="tabChange" listener="#{facilities.saveClicked}" /> <p:tab id="priortabId" title="Prior Sanction/Review Info"> <p:panel id="priorPanelId" header="Prior Sanction/Review Info"> <h:inputHidden id="reviewHidden" value="#{facilities.hiddenReview}" /> <p:inputText value="#{facilities.sanctAuth}" styleClass="textbox" id="psrSanctAID" /> <label><h:outputText value="Sanction Authority" /></label> </p:panel> </p:tab> <!-- Add more tabs with their own hidden fields here if needed --> </p:accordionPanel>
Updated jQuery Code
$(document).ready(function() { // Listen only for input changes inside your target AccordionPanel jQuery(document.body).on('change', '#FacilityAccordId input', function(event) { const $changedInput = $(this); // Find the parent tab panel (PrimeFaces renders p:tab as a div with class ui-tabs-panel) const $tabPanel = $changedInput.closest('div.ui-tabs-panel'); // Get the ID of the parent AccordionPanel const accordionId = $tabPanel.closest('div.ui-accordion').attr('id'); console.log('Changed input belongs to AccordionPanel:', accordionId); // Find the matching hidden field inside this specific tab (works even with PrimeFaces' prefixed IDs) const $hiddenField = $tabPanel.find('[id$="reviewHidden"]'); // Update the hidden field to mark changes $hiddenField.val('true'); // Optional: Trigger an immediate save via remote command if needed // saveTabChanges([{name: 'tabId', value: $tabPanel.attr('id')}]); }); });
Key Details:
- We limit the listener to inputs only inside your AccordionPanel to avoid unrelated input triggers.
closest('div.ui-tabs-panel')targets the exact tab containing the changed input (PrimeFaces uses this class for rendered tabs).[id$="reviewHidden"]uses a jQuery ends-with selector to handle PrimeFaces' auto-generated prefixed IDs (likeformId:FacilityAccordId:priortabId:priorPanelId:reviewHidden).- We grab the parent AccordionPanel ID by traversing up to the
ui-accordioncontainer (the rendered version of yourp:accordionPanel).
PrimeFaces Auto-Save Feasible Solutions
Instead of manually updating hidden fields, here are cleaner, more PrimeFaces-native ways to implement auto-save:
1. Use p:ajax Directly on Inputs
Attach p:ajax to each input to trigger a backend save immediately when the value changes:
<p:inputText value="#{facilities.sanctAuth}" styleClass="textbox" id="psrSanctAID"> <p:ajax event="change" listener="#{facilities.saveField}" update=":messages" /> </p:inputText>
In your managed bean:
public void saveField(AjaxBehaviorEvent event) { // Get the component that triggered the change UIComponent component = event.getComponent(); // Traverse the component hierarchy to get the parent tab/accordion ID if needed String tabId = component.getParent().getParent().getId(); // Save the updated field value to your database/session // ... }
2. Periodic Auto-Save with p:remoteCommand
Set up a timed interval to auto-save all changes periodically (e.g., every 30 seconds):
<p:remoteCommand name="autoSave" action="#{facilities.saveAllChanges}" update=":messages" /> <script> // Auto-save every 30 seconds setInterval(function() { autoSave(); }, 30000); </script>
In your bean:
public void saveAllChanges() { // Save all modified fields from the AccordionPanel // ... }
Combine this with a isDirty flag in your bean to only trigger saves when actual changes exist.
3. Tab Change Triggered Save
Leverage your existing tabChange listener to save changes when the user switches tabs:
- Add a
isDirtyflag for each tab in your managed bean. - On input change, use the jQuery code above to call a remote command that marks the current tab as
isDirty. - In the
tabChangelistener, check if the previous tab was dirty, save its changes, then reset the flag.
内容的提问来源于stack exchange,提问作者Nishant Varshney

